<?php
use Mni\FrontYAML\Parser;
use function _\find;

class Render
{
  public $loader;
  public $twig;
  public $pageInfo;
  public $menu;
  public $background;
  public function __construct()
  {
    $config = new Settings();
    $this->loader = new \Twig\Loader\FilesystemLoader("../content/themes");
    $this->twig = new \Twig\Environment($this->loader, []);
    $settings = $config->getSettings();
    $this->menu = $settings["menu"];
    $this->theme = $settings["global"]["theme"];
    $this->pageInfo = [
      "keywords" => isset($settings["global"]["keywords"])
        ? $settings["global"]["keywords"]
        : "fipamo, blog, jamstack, php, markdown, js",
      "description" => $settings["global"]["descriptions"],
      "image" =>
        $settings["global"]["base_url"] . $settings["global"]["background"],
      "baseURL" => $settings["global"]["base_url"],
    ];
    //move global theme image assets to public folder
    foreach (
      new DirectoryIterator(
        "../content/themes/" . $this->theme . "/assets/images/global/"
      )
      as $file
    ) {
      if ($file->isDot()) {
        continue;
      }
      if (!is_file("../public/assets/images/global/" . $file->getFileName())) {
        copy(
          "../content/themes/" .
            $this->theme .
            "/assets/images/global/" .
            $file->getFileName(),
          "../public/assets/images/global/" . $file->getFileName()
        );
      } else {
        //image is already there, so chill
      }
      //print $file->getFilename() . "\n";
    }

    //copy current theme assets to public
    if (is_file("../public/assets/css/base.css")) {
      unlink("../public/assets/css/base.css");
    }
    copy(
      "../content/themes/" . $this->theme . "/assets/css/base.css",
      "../public/assets/css/base.css"
    );
    if (is_file("../public/assets/scripts/start.min.js")) {
      unlink("../public/assets/scripts/start.min.js");
    }
    copy(
      "../content/themes/" . $this->theme . "/assets/scripts/start.min.js",
      "../public/assets/scripts/start.min.js"
    );
  }

  public function renderPages()
  {
    $pages = (new Book("../content/pages"))->getContents();
    $recent = [];
    $featured = [];
    $limit = 4;
    foreach ($pages as $page) {
      //TODO: Plugin Sorting Class for page options
      if (!$page["deleted"] && $page["published"]) {
        if (count($recent) < $limit) {
          array_push($recent, [
            "path" => $page["path"],
            "slug" => $page["slug"],
            "title" => $page["title"],
            "feature" => $page["feature"],
          ]);
        }

        if ($page["featured"] == true) {
          if (count($featured) < $limit) {
            array_push($featured, [
              "path" => $page["path"],
              "slug" => $page["slug"],
              "title" => $page["title"],
              "feature" => $page["feature"],
            ]);
          }
        }

        $taglist = explode(",", $page["tags"]);
        $tags = [];
        foreach ($taglist as $tag) {
          $label = trim($tag);
          array_push($tags, [
            "label" => $label . " ",
            "slug" => StringTools::safeString($label),
          ]);
        }

        $meta = [
          "who" => $page["author"],
          "when" => $page["created"],
          "tags" => $tags,
        ];

        //render markdown content and clean it
        $parser = new Parser();
        $rendered = $parser->parse($page["content"]);
        $sanitizer = HtmlSanitizer\Sanitizer::create([
          "extensions" => ["basic", "image", "list", "code"],
          "tags" => [
            "img" => [
              "allowed_attributes" => ["src", "alt", "title", "class"],
              "allowed_hosts" => null,
              "allow_relative_links" => true,
            ],
          ],
        ]);

        $scrubbed = $sanitizer->sanitize($rendered->getContent());

        //var_dump($scrubbed);

        //just clean renderd string for now, Sanitize doesn't like relative img urls
        //so another option is needed
        $cleaned = strip_tags($rendered->getContent(), [
          "a",
          "br",
          "p",
          "strong",
          "br",
          "img",
          "iframe",
          "ul",
          "li",
          "i",
          "em",
          "h1",
          "h2",
          "h3",
          "pre",
          "code",
        ]);
        //$cleaned = preg_replace('/(?:\r\n|[\r\n]){2,}/', "\n\n", $cleaned);
        //$cleaned = html_entity_decode($cleaned, ENT_QUOTES, "UTF-8");

        //if page feature isn't empty, replace page info meta image
        if ($page["feature"] != "" || $page["feature"] != null) {
          $this->pageInfo["image"] =
            $this->pageInfo["baseURL"] . $page["feature"];
        }

        if ($page["layout"] == "index") {
          $template = $this->theme . "/index.twig";
          $location = "../public/index.html";
          $dir = null;
          //
          $pageOptions = [
            "title" => $page["title"],
            "background" => $page["feature"],
            "content" => $scrubbed,
            "meta" => $meta,
            "recent" => $recent,
            "featured" => $featured,
            "info" => $this->pageInfo,
            "menu" => $this->menu,
          ];
        } else {
          $template = $this->theme . "/" . $page["layout"] . ".twig";
          $location =
            "../public/" . $page["path"] . "/" . $page["slug"] . ".html";
          $dir = "../public/" . $page["path"];
          $pageOptions = [
            "title" => $page["title"],
            "background" => $page["feature"],
            "content" => $cleaned,
            "meta" => $meta,
            "info" => $this->pageInfo,
            "menu" => $this->menu,
          ];
        }

        $html = $this->twig->render($template, $pageOptions);
        DocTools::writeHTML($location, $html, $dir);
      }
    }
  }

  public function renderArchive()
  {
    $archive = Sorting::archive();
    $template = $this->theme . "/archive.twig";
    $pageOptions = [
      "title" => "Archive",
      "background" => $this->pageInfo["image"],
      "archives" => $archive,
      "info" => $this->pageInfo,
      "menu" => $this->menu,
    ];

    $html = $this->twig->render($template, $pageOptions);
    $location = "../public/archives.html";
    DocTools::writeHTML($location, $html);
  }

  public function renderTags()
  {
    $list = Sorting::tags();
    foreach ($list as $item) {
      $template = $this->theme . "/tags.twig";
      $pageOptions = [
        "title" => "Pages Tagged as " . $item["tag_name"],
        "background" => $this->pageInfo["image"],
        "tag_list" => $item["pages"],
        "info" => $this->pageInfo,
        "menu" => $this->menu,
      ];

      $html = $this->twig->render($template, $pageOptions);

      $location = "../public/tags/" . $item["slug"] . ".html";

      //if tags folder doesn't exist, make it
      if (!is_dir("../public/tags")) {
        mkdir("../public/tags", 0755, true);
      } else {
      }

      if (!is_file($location)) {
        file_put_contents($location, $html);
      } else {
        ($new = fopen($location, "w")) or die("Unable to open file!");
        fwrite($new, $html);
        fclose($new);
      }
    }
  }

  public function renderIndex()
  {
    $pages = (new Book("../content/pages"))->getContents();
    $index = find($pages, ["layout" => "index"]);
    $template = $this->theme . "/index.twig";
    $location = "../public/index.html";
    $dir = null;

    $meta = [
      "who" => $index["author"],
      "when" => $index["created"],
    ];

    $pageOptions = [
      "title" => $index["title"],
      "background" => $index["feature"],
      "meta" => $meta,
    ];

    $html = $this->twig->render($template, $pageOptions);
    DocTools::writeHTML($location, $html, $dir);
  }
}