public StartTemplate <StartModel> GetStartTemplate(string src) { string pageStart = Path.Combine(src, _context.Config.PageStart); if (File.Exists(pageStart)) { _pageStartStack.Push(pageStart); } else if (_pageStartStack.Count > 0) { // Copy it from the parent directory. _pageStartStack.Push(_pageStartStack.Peek()); } else { _pageStartStack.Push(String.Empty); } StartTemplate <StartModel> startTemplate = null; if (_pageStartStack.Count > 0 && !String.IsNullOrWhiteSpace(_pageStartStack.Peek())) { startTemplate = ProcessStartFile(_pageStartStack.Peek()); } return(startTemplate); }
void Walk(string srcDir, string srcPart, string dstDir, string dstPart, bool write, int depth) { string src = Path.Combine(srcDir, srcPart); string dst = Path.Combine(dstDir, dstPart); var dir = new DirectoryInfo(src); StartTemplate <StartModel> startTemplate = _startProcessor.GetStartTemplate(src); foreach (var file in dir.GetFiles()) { string ext = Path.GetExtension(file.Name); if (file.Name.Equals(_config.PageStart, StringComparison.OrdinalIgnoreCase)) { // Page start is handled via the page start stack. } else if (ext == ".md" || ext == ".markdown") { ProcessFile(src, dst, file.Name, write, startTemplate, _markdownProcessor); } else if (ext == ".cshtml") { ProcessFile(src, dst, file.Name, write, startTemplate, _razorProcessor); } else { string dstpath = Path.Combine(dst, file.Name); if (write) { Directory.CreateDirectory(dst); File.Copy(file.FullName, dstpath, true); } } } foreach (var subdir in dir.GetDirectories()) { Walk(src, subdir.Name, dst, subdir.Name, write, depth + 1); } }
public override PageTemplate <PageModel> ProcessFile(string src, string dst, string name, PageModel model, StartTemplate <StartModel> startTemplate, Action <string, string> writer) { string front; string markdown; using (var reader = new StreamReader(src)) { ReadMarkdown(reader, out front, out markdown); } string cshtml = "@{\r\n" + front + "}\r\n" + _markdown.Transform(markdown); try { return(ProcessRazorTemplate(cshtml, src, dst, name, model, startTemplate, writer)); } catch (Exception ex) { throw new PageProcessingException("Error processing Markdown file.", src, cshtml, ex); } }
protected PageTemplate <PageModel> ProcessRazorTemplate(string cshtml, string path, string dst, string name, PageModel model, StartTemplate <StartModel> startTemplate, Action <string, string> writer) { // NOTE: On the first pass (scan), we don't have a destination. if (!String.IsNullOrWhiteSpace(dst)) { // Set global page depth. Lame but OK since we're single threaded. _context.PageDepth = FileUtility.GetDepthFromPath(_context.DestinationDir, dst); } else { _context.PageDepth = 0; } // This model state changes from page to page. model.Source = FileUtility.GetRelativePath(_context.SourceDir, path); // The page may reference it's own info. if (model.PageMap.ContainsKey(model.Source)) { model.PageInfo = model.PageMap[model.Source]; } else { // Provide a default on the scan pass to obviate null checks. model.PageInfo = new PageInfo(); } // Create an instance of the page template for this cshtml. if (!_context.PageTemplateService.HasTemplate(name)) { _context.PageTemplateService.Compile(cshtml, typeof(PageModel), name); } var instance = _context.PageTemplateService.GetTemplate(cshtml, model, name); // Apply any _PageStart defaults. var pageTemplate = instance as PageTemplate <PageModel>; if (pageTemplate != null && startTemplate != null) { if (startTemplate.ForceLayout || (String.IsNullOrWhiteSpace(pageTemplate.Layout) && !String.IsNullOrWhiteSpace(startTemplate.Layout))) { pageTemplate.Layout = startTemplate.Layout; } } string result = _context.PageTemplateService.Run(instance); if (writer != null) { writer(dst, result); } return(pageTemplate); }
public virtual PageTemplate <PageModel> ProcessFile(string src, string dst, string name, PageModel model, StartTemplate <StartModel> startTemplate, Action <string, string> writer) { string cshtml; using (var reader = new StreamReader(src)) { cshtml = reader.ReadToEnd(); } try { return(ProcessRazorTemplate(cshtml, src, dst, name, model, startTemplate, writer)); } catch (Exception ex) { throw new PageProcessingException("Error processing Razor file.", src, cshtml, ex); } }
void ProcessFile(string src, string dst, string file, bool write, StartTemplate <StartModel> startTemplate, IPageProcessor processor) { #if DEBUG // Console.Write("."); #endif string srcfile = Path.Combine(src, file); string dstfile = null; Action <string, string> writer = null; if (write) { if (!_context.PageMap.ContainsKey(srcfile)) { // This file is unpublished. return; } PageInfo pageInfo = _context.PageMap[srcfile]; dstfile = pageInfo.GetDestinationPath(_context, src, dst, file); string dstdir = Path.GetDirectoryName(dstfile); Directory.CreateDirectory(dstdir); if (_context.Options.Verbose) { Console.WriteLine(dstfile); } writer = (d, r) => { // Write the output file if a destination is specified. if (!String.IsNullOrWhiteSpace(d)) { File.WriteAllText(d, r); } }; } PageTemplate <PageModel> pageTemplate = processor.ProcessFile(srcfile, dstfile, srcfile, _pageModel, startTemplate, writer); if (!write && pageTemplate.Published) { // Force the use of an empty layout to get the just the content. var contentStart = new StartTemplate <StartModel>() { ForceLayout = true }; string content = null; PageTemplate <PageModel> excerptTemplate = processor.ProcessFile(srcfile, null, srcfile + "*", _pageModel, contentStart, (d, r) => { content = r; }); if (pageTemplate.Excerpt == null) { pageTemplate.Excerpt = ExtractExcerpt(content); } // If this file is named like a post, get the info. PathInfo pathInfo = PathInfo.GetpathInfo(src, file); DateTime date = pageTemplate.Date.HasValue ? pageTemplate.Date.Value : (pathInfo == null ? DateTime.MinValue : pathInfo.Date); if (date == DateTime.MinValue) { // Note: It's probably OK for pages not to have dates, // since they won't often be listed by date. // Console.WriteLine("Warning: No date specified for {0}.", srcfile); } PageInfo pageInfo; if (pathInfo != null) { pageInfo = new PostInfo(pathInfo); } else { pageInfo = new PageInfo(); } pageInfo.Permalink = pageTemplate.Permalink; pageInfo.Rebase = pageTemplate.Rebase; pageInfo.Title = pageTemplate.Title; pageInfo.Content = content; pageInfo.Excerpt = pageTemplate.Excerpt; pageInfo.Categories = pageTemplate.Categories; // TODO: Copy pageInfo.Tags = pageTemplate.Tags; // TODO: Copy pageInfo.Date = date; dstfile = pageInfo.GetDestinationPath(_context, src, dst, file); // Build a URL fragment for internal linking. pageInfo.Url = FileUtility.GetInternalUrl(_context, dstfile); AddCategories(pageInfo, pageTemplate.Categories); AddTags(pageInfo, pageTemplate.Tags); _context.PageMap.Add(srcfile, pageInfo); } }