Remove silly DOCTYPE
[scpubgit/App-SCS.git] / lib / App / SCS / PageSet.pm
index b71c5d4..3f3d5d6 100644 (file)
@@ -7,9 +7,11 @@ use Syntax::Keyword::Gather;
 use App::SCS::Page;
 use IO::All;
 use Try::Tiny;
-use List::Util qw(reduce);
-use JSON;
+use List::Util qw(reduce max);
+use Module::Runtime qw(use_module);
+use JSON::MaybeXS;
 use Moo;
+use JSONY;
 
 with 'App::SCS::Role::PageChildren';
 
@@ -32,6 +34,7 @@ sub _build_rel_path {
     ->catdir(File::Spec->abs2rel($self->base_dir->name, $self->top_dir->name))
 }
 
+sub _page_set { $_[0] }
 sub _page_set_class { ref($_[0]) }
 sub _top_dir { shift->top_dir }
 sub _my_path { shift->base_dir }
@@ -56,12 +59,25 @@ sub get {
   );
 }
 
+sub _config_files_for {
+  my ($self, $path) = @_;
+
+  my @dir_parts = io->dir($path)->splitdir;
+  my @dirs = map io->dir('')->catdir(@dir_parts[1..$_]), 1..($#dir_parts - 1);
+
+  return grep +(-f $_->name and not $_->empty),
+           map $self->_top_dir->catfile("${_}.conf"), @dirs;
+}
+
 sub _inflate {
   my ($self, $type, $path, $io) = @_;
   (my $cache_name = $io->name) =~ s/\/([^\/]+)$/\/.htcache.$1.json/;
   my $cache = io($cache_name);
+  my @config_files = $self->_config_files_for($path);
+  my $max_stat = max map $_->mtime, $io, @config_files;
+
   if (-f $cache_name) {
-    if ($cache->mtime >= $io->mtime) {
+    if ($cache->mtime >= $max_stat) {
       return try {
         $self->_new_page($path, $self->_json->decode($cache->all));
       } catch {
@@ -71,9 +87,27 @@ sub _inflate {
   }
   my $raw = $io->all;
   try {
+
     my $extracted = $self->${\"_extract_from_${type}"}($raw);
-    try { $cache->print($self->_json->encode($extracted)); };
-    $self->_new_page($path, $extracted);
+    my $jsony = JSONY->new;
+
+    my $setup = {
+      %$extracted,
+      plugin_config => [
+        map @{$jsony->load($_)}, (
+          $extracted->{plugins},
+          (map $_->all, reverse @config_files), # apply config deepest first
+        )
+      ]
+    };
+
+    try {
+        my $tmp_cache = io($cache_name . ".tmp");
+        $tmp_cache->print($self->_json->encode($setup));
+        $tmp_cache->rename($cache_name);
+    };
+
+    $self->_new_page($path, $setup);
   } catch {
     die "Error inflating ${path} as ${type}: $_\n";
   }
@@ -131,15 +165,16 @@ sub _all_files {
 
 sub latest {
   my ($self, $max) = @_;
-  require SCSite::LatestPageSet;
-  SCSite::LatestPageSet->new(
+  use_module('App::SCS::LatestPageSet')->new(
     parent => $self,
     max_entries => $max,
   );
 }
 
 sub _new_page {
-  SCSite::Page->new({ path => $_[1], page_set => $_[0], %{$_[2]} })
+  use_module('App::SCS::Page')->new(
+    path => $_[1], page_set => $_[0], %{$_[2]}
+  );
 }
 
 sub _types_re { qw/\.(html|md)/ }
@@ -165,8 +200,11 @@ sub _extract_from_html {
 
 sub _extract_from_md {
   my ($self, $md) = @_;
-  #warn markdown($md, { document_format => 'complete' });
-  $self->_extract_from_html(markdown($md, { document_format => 'complete' }));
+
+  my $html = markdown($md, { document_format => 'complete' });
+
+  $html =~ s#<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">##g;
+  $self->_extract_from_html($html);
 }
 
 1;