예제 #1
0
        public List <TocEntry> ExtractTocEntries(string markdown)
        {
            var pipeline = DocgenDefaults.GetDefaultPipeline();
            var document = Markdig.Markdown.Parse(markdown, pipeline);

            var result = new List <TocEntry>();

            void WalkBlock(Block block)
            {
                if (block is HeadingBlock headingBlock)
                {
                    result.Add(new TocEntry
                    {
                        Level = headingBlock.Level,
                        Id    = headingBlock.TryGetAttributes().Id,
                        Title = MarkdownHelpers.RenderLeafInlineRaw(headingBlock)
                    });
                }
                if (block is CustomContainer customContainer)
                {
                    foreach (var child in customContainer)
                    {
                        WalkBlock(child);
                    }
                }
            }

            foreach (var item in document)
            {
                WalkBlock(item);
            }

            return(result);
        }
예제 #2
0
        public MarkdownRenderResult RenderMarkdown(string markdown)
        {
            var yaml = _yamlParser.ParseYaml(markdown);

            var html = Markdig.Markdown.ToHtml(yaml.Markdown, DocgenDefaults.GetDefaultPipeline());

            if (!string.IsNullOrEmpty(html))
            {
                html = html.TrimEnd(Environment.NewLine.ToCharArray());
            }

            return(new MarkdownRenderResult(yaml.Yaml, html));
        }
예제 #3
0
        public string TransformLinks(string markdown, Func <string, string> func)
        {
            using (var stringWriter = new StringWriter())
            {
                var transformRenderer = new MarkdownTransformRenderer(stringWriter, markdown);
                transformRenderer.ObjectRenderers.Add(new LinkTransformRenderer(func));

                var document = Markdig.Markdown.Parse(markdown, DocgenDefaults.GetDefaultPipeline());

                transformRenderer.Render(document);

                // Flush any remaining markdown content.
                transformRenderer.Writer.Write(transformRenderer.TakeNext(transformRenderer.OriginalMarkdown.Length - transformRenderer.LastWrittenIndex));

                stringWriter.Flush();

                return(stringWriter.ToString());
            }
        }
예제 #4
0
        public async Task <IManualWeb> BuildManual()
        {
            var webBuilder = _serviceProvider.GetRequiredService <IWebBuilder>();

            var resourcesDirectory = Path.Combine(_options.ContentDirectory, "resources");

            if (await Task.Run(() => Directory.Exists(resourcesDirectory)))
            {
                webBuilder.RegisterDirectory("/resources", resourcesDirectory);
            }

            webBuilder.RegisterMvc("/", new
            {
                controller = "Home",
                action     = "Index"
            });

            var languages = await _manualTranslations.GetLanguages();

            foreach (var language in languages)
            {
                webBuilder.RegisterMvc($"/prince/{language}/template", new
                {
                    controller = "Prince",
                    action     = "Template",
                    language
                });

                webBuilder.RegisterMvc($"/prince/{language}/output.pdf", new
                {
                    controller = "Prince",
                    action     = "Pdf",
                    language
                });
            }

            // Register our static files.
            webBuilder.RegisterDirectory("/Users/pknopf/git/docgen/src/DocGen.Web.Manual/Internal/Resources/wwwroot");

            CoversheetConfig coversheet = null;
            var sections = new ManualSectionStore();

            foreach (var markdownFile in await Task.Run(() => Directory.GetFiles(_options.ContentDirectory, "*.md")))
            {
                var content = await Task.Run(() => File.ReadAllText(markdownFile));

                var yaml = _yamlParser.ParseYaml(content);
                if (yaml.Yaml == null)
                {
                    yaml = new YamlParseResult(JsonConvert.DeserializeObject("{}"), yaml.Markdown);
                }

                var type = "Content";
                if (!string.IsNullOrEmpty((string)yaml.Yaml.Type))
                {
                    type = yaml.Yaml.Type;
                }

                switch (type)
                {
                case "Coversheet":
                    if (coversheet != null)
                    {
                        throw new DocGenException("Multiple coversheets detected");
                    }
                    coversheet = new CoversheetConfig();
                    coversheet.ProductImage = yaml.Yaml.ProductImage;
                    coversheet.ProductLogo  = yaml.Yaml.ProductLogo;
                    coversheet.Model        = yaml.Yaml.Model;
                    coversheet.Text         = yaml.Yaml.Text;
                    break;

                case "Content":
                    var order = (int?)yaml.Yaml.Order;
                    var title = (string)yaml.Yaml.Title;
                    if (string.IsNullOrEmpty(title))
                    {
                        throw new DocGenException($"The file {markdownFile} needs a title.");
                    }
                    foreach (var language in languages)
                    {
                        sections.AddMarkdown(language,
                                             _translator.Translate(language, title)
                                             , order ?? 0,
                                             _markdownTransformer.TransformMarkdown(
                                                 yaml.Markdown,
                                                 DocgenDefaults.GetDefaultPipeline(),
                                                 x => _translator.Translate(language, x)),
                                             markdownFile);
                    }
                    break;

                default:
                    throw new DocGenException("Unknown contente type");
                }
            }

            if (coversheet == null)
            {
                throw new DocGenException("You must provide a coversheet");
            }

            webBuilder.RegisterServices(services => {
                services.AddMvc();
                services.Configure <RazorViewEngineOptions>(options =>
                {
                    options.FileProviders.Add(new PhysicalFileProvider("/Users/pknopf/git/docgen/src/DocGen.Web.Manual/Internal/Resources"));
                    var templateDirectory = Path.Combine(_options.ContentDirectory, "templates");
                    if (Directory.Exists(templateDirectory))
                    {
                        options.FileProviders.Add(new PhysicalFileProvider(templateDirectory));
                    }
                });
                services.AddSingleton(_translator);
                services.AddSingleton(_manualTranslations);
                services.AddSingleton(sections);
                services.AddSingleton(coversheet);
                services.AddSingleton(_symbolGlossaryStore);
                // These regitrations are so that our controllers can inject core DocGen services.
                DocGen.Core.Services.Register(services);
            });

            return(new ManualWeb(webBuilder));
        }
예제 #5
0
        public async Task RegenerateTemplate()
        {
            var translations = new List <string>();

            foreach (var markdownFile in await Task.Run(() => Directory.GetFiles(_options.ContentDirectory, "*.md")))
            {
                var content = await Task.Run(() => File.ReadAllText(markdownFile));

                var yaml = _yamlParser.ParseYaml(content);
                if (yaml.Yaml == null)
                {
                    yaml = new YamlParseResult(JsonConvert.DeserializeObject("{}"), yaml.Markdown);
                }

                var type = "Content";
                if (!string.IsNullOrEmpty((string)yaml.Yaml.Type))
                {
                    type = yaml.Yaml.Type;
                }

                switch (type)
                {
                case "Content":
                    var order = (int?)yaml.Yaml.Order;
                    _markdownTransformer.TransformMarkdown(yaml.Markdown,
                                                           DocgenDefaults.GetDefaultPipeline(),
                                                           value =>
                    {
                        if (!translations.Contains(value))
                        {
                            translations.Add(value);
                        }
                        return(value);
                    });
                    break;
                }
            }

            // Add some translations that we have hardcoded in our templates.
            if (!translations.Contains("Table of contents"))
            {
                translations.Add("Table of contents");
            }

            // Now that we have the translations of all of our documents, let's generate the POT file.
            var destination = Path.Combine(_options.ContentDirectory, "translations", "template.pot");
            await Task.Run(() =>
            {
                var parentDirectory = Path.GetDirectoryName(destination) ?? "";
                if (!Directory.Exists(parentDirectory))
                {
                    Directory.CreateDirectory(parentDirectory);
                }
                if (File.Exists(destination))
                {
                    File.Delete(destination);
                }
                using (var file = File.OpenWrite(destination))
                    using (var writer = new StreamWriter(file))
                        SharpGettext.SharpGettext.GeneratePOT(
                            new POTemplateHeader
                        {
                            Language = "en-US"
                        },
                            translations.Select(x => new POTranslation
                        {
                            Text = x
                        }).ToList(),
                            writer);
            });

            // Now that we have our POT files, let's update all of our translations.
            await Task.Run(async() =>
            {
                foreach (var file in Directory.GetFiles(Path.Combine(_options.ContentDirectory, "translations"), "*.po"))
                {
                    await RunAsync("msgmerge", $"-U \"{file}\" \"{destination}\"");
                }
            });
        }