mirror of
https://github.com/go-gitea/gitea.git
synced 2026-02-07 09:49:41 +09:00
@@ -22,8 +22,9 @@ func TestEntriesCustomSort(t *testing.T) {
|
||||
&TreeEntry{name: "b-file", entryMode: EntryModeBlob},
|
||||
}
|
||||
expected := slices.Clone(entries)
|
||||
rand.Shuffle(len(entries), func(i, j int) { entries[i], entries[j] = entries[j], entries[i] })
|
||||
assert.NotEqual(t, expected, entries)
|
||||
for slices.Equal(expected, entries) {
|
||||
rand.Shuffle(len(entries), func(i, j int) { entries[i], entries[j] = entries[j], entries[i] })
|
||||
}
|
||||
entries.CustomSort(strings.Compare)
|
||||
assert.Equal(t, expected, entries)
|
||||
}
|
||||
|
||||
@@ -20,14 +20,12 @@ func init() {
|
||||
// See https://github.com/asciinema/asciinema/blob/develop/doc/asciicast-v2.md
|
||||
type Renderer struct{}
|
||||
|
||||
// Name implements markup.Renderer
|
||||
func (Renderer) Name() string {
|
||||
return "asciicast"
|
||||
}
|
||||
|
||||
// Extensions implements markup.Renderer
|
||||
func (Renderer) Extensions() []string {
|
||||
return []string{".cast"}
|
||||
func (Renderer) FileNamePatterns() []string {
|
||||
return []string{"*.cast"}
|
||||
}
|
||||
|
||||
const (
|
||||
@@ -35,12 +33,10 @@ const (
|
||||
playerSrcAttr = "data-asciinema-player-src"
|
||||
)
|
||||
|
||||
// SanitizerRules implements markup.Renderer
|
||||
func (Renderer) SanitizerRules() []setting.MarkupSanitizerRule {
|
||||
return []setting.MarkupSanitizerRule{{Element: "div", AllowAttr: playerSrcAttr}}
|
||||
}
|
||||
|
||||
// Render implements markup.Renderer
|
||||
func (Renderer) Render(ctx *markup.RenderContext, _ io.Reader, output io.Writer) error {
|
||||
rawURL := fmt.Sprintf("%s/%s/%s/raw/%s/%s",
|
||||
setting.AppSubURL,
|
||||
|
||||
@@ -20,29 +20,24 @@ func init() {
|
||||
markup.RegisterRenderer(Renderer{})
|
||||
}
|
||||
|
||||
// Renderer implements markup.Renderer
|
||||
type Renderer struct{}
|
||||
|
||||
var _ markup.RendererContentDetector = (*Renderer)(nil)
|
||||
|
||||
// Name implements markup.Renderer
|
||||
func (Renderer) Name() string {
|
||||
return "console"
|
||||
}
|
||||
|
||||
// Extensions implements markup.Renderer
|
||||
func (Renderer) Extensions() []string {
|
||||
return []string{".sh-session"}
|
||||
func (Renderer) FileNamePatterns() []string {
|
||||
return []string{"*.sh-session"}
|
||||
}
|
||||
|
||||
// SanitizerRules implements markup.Renderer
|
||||
func (Renderer) SanitizerRules() []setting.MarkupSanitizerRule {
|
||||
return []setting.MarkupSanitizerRule{
|
||||
{Element: "span", AllowAttr: "class", Regexp: `^term-((fg[ix]?|bg)\d+|container)$`},
|
||||
}
|
||||
}
|
||||
|
||||
// CanRender implements markup.RendererContentDetector
|
||||
func (Renderer) CanRender(filename string, sniffedType typesniffer.SniffedType, prefetchBuf []byte) bool {
|
||||
if !sniffedType.IsTextPlain() {
|
||||
return false
|
||||
|
||||
@@ -20,20 +20,16 @@ func init() {
|
||||
markup.RegisterRenderer(Renderer{})
|
||||
}
|
||||
|
||||
// Renderer implements markup.Renderer for csv files
|
||||
type Renderer struct{}
|
||||
|
||||
// Name implements markup.Renderer
|
||||
func (Renderer) Name() string {
|
||||
return "csv"
|
||||
}
|
||||
|
||||
// Extensions implements markup.Renderer
|
||||
func (Renderer) Extensions() []string {
|
||||
return []string{".csv", ".tsv"}
|
||||
func (Renderer) FileNamePatterns() []string {
|
||||
return []string{"*.csv", "*.tsv"}
|
||||
}
|
||||
|
||||
// SanitizerRules implements markup.Renderer
|
||||
func (Renderer) SanitizerRules() []setting.MarkupSanitizerRule {
|
||||
return []setting.MarkupSanitizerRule{
|
||||
{Element: "table", AllowAttr: "class", Regexp: `^data-table$`},
|
||||
|
||||
13
modules/markup/external/external.go
vendored
13
modules/markup/external/external.go
vendored
@@ -21,10 +21,9 @@ import (
|
||||
|
||||
// RegisterRenderers registers all supported third part renderers according settings
|
||||
func RegisterRenderers() {
|
||||
markup.RegisterRenderer(&openAPIRenderer{})
|
||||
for _, renderer := range setting.ExternalMarkupRenderers {
|
||||
if renderer.Enabled && renderer.Command != "" && len(renderer.FileExtensions) > 0 {
|
||||
markup.RegisterRenderer(&Renderer{renderer})
|
||||
}
|
||||
markup.RegisterRenderer(&Renderer{renderer})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -38,22 +37,18 @@ var (
|
||||
_ markup.ExternalRenderer = (*Renderer)(nil)
|
||||
)
|
||||
|
||||
// Name returns the external tool name
|
||||
func (p *Renderer) Name() string {
|
||||
return p.MarkupName
|
||||
}
|
||||
|
||||
// NeedPostProcess implements markup.Renderer
|
||||
func (p *Renderer) NeedPostProcess() bool {
|
||||
return p.MarkupRenderer.NeedPostProcess
|
||||
}
|
||||
|
||||
// Extensions returns the supported extensions of the tool
|
||||
func (p *Renderer) Extensions() []string {
|
||||
return p.FileExtensions
|
||||
func (p *Renderer) FileNamePatterns() []string {
|
||||
return p.FilePatterns
|
||||
}
|
||||
|
||||
// SanitizerRules implements markup.Renderer
|
||||
func (p *Renderer) SanitizerRules() []setting.MarkupSanitizerRule {
|
||||
return p.MarkupSanitizerRules
|
||||
}
|
||||
|
||||
79
modules/markup/external/openapi.go
vendored
Normal file
79
modules/markup/external/openapi.go
vendored
Normal file
@@ -0,0 +1,79 @@
|
||||
// Copyright 2026 The Gitea Authors. All rights reserved.
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
package external
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"html"
|
||||
"io"
|
||||
|
||||
"code.gitea.io/gitea/modules/markup"
|
||||
"code.gitea.io/gitea/modules/setting"
|
||||
"code.gitea.io/gitea/modules/util"
|
||||
)
|
||||
|
||||
type openAPIRenderer struct{}
|
||||
|
||||
var (
|
||||
_ markup.PostProcessRenderer = (*openAPIRenderer)(nil)
|
||||
_ markup.ExternalRenderer = (*openAPIRenderer)(nil)
|
||||
)
|
||||
|
||||
func (p *openAPIRenderer) Name() string {
|
||||
return "openapi"
|
||||
}
|
||||
|
||||
func (p *openAPIRenderer) NeedPostProcess() bool {
|
||||
return false
|
||||
}
|
||||
|
||||
func (p *openAPIRenderer) FileNamePatterns() []string {
|
||||
return []string{
|
||||
"openapi.yaml",
|
||||
"openapi.yml",
|
||||
"openapi.json",
|
||||
"swagger.yaml",
|
||||
"swagger.yml",
|
||||
"swagger.json",
|
||||
}
|
||||
}
|
||||
|
||||
func (p *openAPIRenderer) SanitizerRules() []setting.MarkupSanitizerRule {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (p *openAPIRenderer) GetExternalRendererOptions() (ret markup.ExternalRendererOptions) {
|
||||
ret.SanitizerDisabled = true
|
||||
ret.DisplayInIframe = true
|
||||
ret.ContentSandbox = ""
|
||||
return ret
|
||||
}
|
||||
|
||||
func (p *openAPIRenderer) Render(ctx *markup.RenderContext, input io.Reader, output io.Writer) error {
|
||||
content, err := util.ReadWithLimit(input, int(setting.UI.MaxDisplayFileSize))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
// TODO: can extract this to a tmpl file later
|
||||
_, err = io.WriteString(output, fmt.Sprintf(
|
||||
`<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||
<link rel="stylesheet" href="%s/assets/css/swagger.css?v=%s">
|
||||
</head>
|
||||
<body>
|
||||
<div id="swagger-ui"><textarea class="swagger-spec-content" data-spec-filename="%s">%s</textarea></div>
|
||||
<script src="%s/assets/js/swagger.js?v=%s"></script>
|
||||
</body>
|
||||
</html>`,
|
||||
setting.StaticURLPrefix,
|
||||
setting.AssetVersion,
|
||||
html.EscapeString(ctx.RenderOptions.RelativePath),
|
||||
html.EscapeString(util.UnsafeBytesToString(content)),
|
||||
setting.StaticURLPrefix,
|
||||
setting.AssetVersion,
|
||||
))
|
||||
return err
|
||||
}
|
||||
@@ -14,5 +14,7 @@ import (
|
||||
func TestMain(m *testing.M) {
|
||||
setting.IsInTesting = true
|
||||
markup.RenderBehaviorForTesting.DisableAdditionalAttributes = true
|
||||
setting.Markdown.FileNamePatterns = []string{"*.md"}
|
||||
markup.RefreshFileNamePatterns()
|
||||
os.Exit(m.Run())
|
||||
}
|
||||
|
||||
@@ -240,30 +240,24 @@ func init() {
|
||||
markup.RegisterRenderer(Renderer{})
|
||||
}
|
||||
|
||||
// Renderer implements markup.Renderer
|
||||
type Renderer struct{}
|
||||
|
||||
var _ markup.PostProcessRenderer = (*Renderer)(nil)
|
||||
|
||||
// Name implements markup.Renderer
|
||||
func (Renderer) Name() string {
|
||||
return MarkupName
|
||||
}
|
||||
|
||||
// NeedPostProcess implements markup.PostProcessRenderer
|
||||
func (Renderer) NeedPostProcess() bool { return true }
|
||||
|
||||
// Extensions implements markup.Renderer
|
||||
func (Renderer) Extensions() []string {
|
||||
return setting.Markdown.FileExtensions
|
||||
func (Renderer) FileNamePatterns() []string {
|
||||
return setting.Markdown.FileNamePatterns
|
||||
}
|
||||
|
||||
// SanitizerRules implements markup.Renderer
|
||||
func (Renderer) SanitizerRules() []setting.MarkupSanitizerRule {
|
||||
return []setting.MarkupSanitizerRule{}
|
||||
}
|
||||
|
||||
// Render implements markup.Renderer
|
||||
func (Renderer) Render(ctx *markup.RenderContext, input io.Reader, output io.Writer) error {
|
||||
return render(ctx, input, output)
|
||||
}
|
||||
|
||||
@@ -31,20 +31,16 @@ var (
|
||||
_ markup.PostProcessRenderer = (*renderer)(nil)
|
||||
)
|
||||
|
||||
// Name implements markup.Renderer
|
||||
func (renderer) Name() string {
|
||||
return "orgmode"
|
||||
}
|
||||
|
||||
// NeedPostProcess implements markup.PostProcessRenderer
|
||||
func (renderer) NeedPostProcess() bool { return true }
|
||||
|
||||
// Extensions implements markup.Renderer
|
||||
func (renderer) Extensions() []string {
|
||||
return []string{".org"}
|
||||
func (renderer) FileNamePatterns() []string {
|
||||
return []string{"*.org"}
|
||||
}
|
||||
|
||||
// SanitizerRules implements markup.Renderer
|
||||
func (renderer) SanitizerRules() []setting.MarkupSanitizerRule {
|
||||
return []setting.MarkupSanitizerRule{}
|
||||
}
|
||||
|
||||
@@ -4,6 +4,7 @@
|
||||
package markup
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"context"
|
||||
"fmt"
|
||||
"html/template"
|
||||
@@ -16,6 +17,7 @@ import (
|
||||
"code.gitea.io/gitea/modules/htmlutil"
|
||||
"code.gitea.io/gitea/modules/markup/internal"
|
||||
"code.gitea.io/gitea/modules/setting"
|
||||
"code.gitea.io/gitea/modules/typesniffer"
|
||||
"code.gitea.io/gitea/modules/util"
|
||||
|
||||
"golang.org/x/sync/errgroup"
|
||||
@@ -144,22 +146,29 @@ func (ctx *RenderContext) WithHelper(helper RenderHelper) *RenderContext {
|
||||
return ctx
|
||||
}
|
||||
|
||||
// FindRendererByContext finds renderer by RenderContext
|
||||
// TODO: it should be merged with other similar functions like GetRendererByFileName, DetectMarkupTypeByFileName, etc
|
||||
func FindRendererByContext(ctx *RenderContext) (Renderer, error) {
|
||||
func (ctx *RenderContext) DetectMarkupRenderer(prefetchBuf []byte) Renderer {
|
||||
if ctx.RenderOptions.MarkupType == "" && ctx.RenderOptions.RelativePath != "" {
|
||||
ctx.RenderOptions.MarkupType = DetectMarkupTypeByFileName(ctx.RenderOptions.RelativePath)
|
||||
if ctx.RenderOptions.MarkupType == "" {
|
||||
return nil, util.NewInvalidArgumentErrorf("unsupported file to render: %q", ctx.RenderOptions.RelativePath)
|
||||
var sniffedType typesniffer.SniffedType
|
||||
if len(prefetchBuf) > 0 {
|
||||
sniffedType = typesniffer.DetectContentType(prefetchBuf)
|
||||
}
|
||||
ctx.RenderOptions.MarkupType = DetectRendererTypeByPrefetch(ctx.RenderOptions.RelativePath, sniffedType, prefetchBuf)
|
||||
}
|
||||
return renderers[ctx.RenderOptions.MarkupType]
|
||||
}
|
||||
|
||||
renderer := renderers[ctx.RenderOptions.MarkupType]
|
||||
func (ctx *RenderContext) DetectMarkupRendererByReader(in io.Reader) (Renderer, io.Reader, error) {
|
||||
prefetchBuf := make([]byte, 512)
|
||||
n, err := util.ReadAtMost(in, prefetchBuf)
|
||||
if err != nil && err != io.EOF {
|
||||
return nil, nil, err
|
||||
}
|
||||
prefetchBuf = prefetchBuf[:n]
|
||||
renderer := ctx.DetectMarkupRenderer(prefetchBuf)
|
||||
if renderer == nil {
|
||||
return nil, util.NewNotExistErrorf("unsupported markup type: %q", ctx.RenderOptions.MarkupType)
|
||||
return nil, nil, util.NewInvalidArgumentErrorf("unable to find a render")
|
||||
}
|
||||
|
||||
return renderer, nil
|
||||
return renderer, io.MultiReader(bytes.NewReader(prefetchBuf), in), nil
|
||||
}
|
||||
|
||||
func RendererNeedPostProcess(renderer Renderer) bool {
|
||||
@@ -170,12 +179,12 @@ func RendererNeedPostProcess(renderer Renderer) bool {
|
||||
}
|
||||
|
||||
// Render renders markup file to HTML with all specific handling stuff.
|
||||
func Render(ctx *RenderContext, input io.Reader, output io.Writer) error {
|
||||
renderer, err := FindRendererByContext(ctx)
|
||||
func Render(rctx *RenderContext, origInput io.Reader, output io.Writer) error {
|
||||
renderer, input, err := rctx.DetectMarkupRendererByReader(origInput)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
return RenderWithRenderer(ctx, renderer, input, output)
|
||||
return RenderWithRenderer(rctx, renderer, input, output)
|
||||
}
|
||||
|
||||
// RenderString renders Markup string to HTML with all specific handling stuff and return string
|
||||
@@ -287,12 +296,14 @@ func Init(renderHelpFuncs *RenderHelperFuncs) {
|
||||
}
|
||||
|
||||
// since setting maybe changed extensions, this will reload all renderer extensions mapping
|
||||
extRenderers = make(map[string]Renderer)
|
||||
fileNameRenderers = make(map[string]Renderer)
|
||||
for _, renderer := range renderers {
|
||||
for _, ext := range renderer.Extensions() {
|
||||
extRenderers[strings.ToLower(ext)] = renderer
|
||||
for _, pattern := range renderer.FileNamePatterns() {
|
||||
fileNameRenderers[pattern] = renderer
|
||||
}
|
||||
}
|
||||
|
||||
RefreshFileNamePatterns()
|
||||
}
|
||||
|
||||
func ComposeSimpleDocumentMetas() map[string]string {
|
||||
|
||||
@@ -14,8 +14,8 @@ import (
|
||||
|
||||
// Renderer defines an interface for rendering markup file to HTML
|
||||
type Renderer interface {
|
||||
Name() string // markup format name
|
||||
Extensions() []string
|
||||
Name() string // markup format name, also the renderer type, also the external tool name
|
||||
FileNamePatterns() []string
|
||||
SanitizerRules() []setting.MarkupSanitizerRule
|
||||
Render(ctx *RenderContext, input io.Reader, output io.Writer) error
|
||||
}
|
||||
@@ -43,26 +43,52 @@ type RendererContentDetector interface {
|
||||
}
|
||||
|
||||
var (
|
||||
extRenderers = make(map[string]Renderer)
|
||||
renderers = make(map[string]Renderer)
|
||||
fileNameRenderers = make(map[string]Renderer)
|
||||
renderers = make(map[string]Renderer)
|
||||
)
|
||||
|
||||
// RegisterRenderer registers a new markup file renderer
|
||||
func RegisterRenderer(renderer Renderer) {
|
||||
// TODO: need to handle conflicts
|
||||
renderers[renderer.Name()] = renderer
|
||||
for _, ext := range renderer.Extensions() {
|
||||
extRenderers[strings.ToLower(ext)] = renderer
|
||||
}
|
||||
|
||||
func RefreshFileNamePatterns() {
|
||||
// TODO: need to handle conflicts
|
||||
fileNameRenderers = make(map[string]Renderer)
|
||||
for _, renderer := range renderers {
|
||||
for _, ext := range renderer.FileNamePatterns() {
|
||||
fileNameRenderers[strings.ToLower(ext)] = renderer
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// GetRendererByFileName get renderer by filename
|
||||
func GetRendererByFileName(filename string) Renderer {
|
||||
extension := strings.ToLower(path.Ext(filename))
|
||||
return extRenderers[extension]
|
||||
func DetectRendererTypeByFilename(filename string) Renderer {
|
||||
basename := path.Base(strings.ToLower(filename))
|
||||
ext1 := path.Ext(basename)
|
||||
if renderer := fileNameRenderers[basename]; renderer != nil {
|
||||
return renderer
|
||||
}
|
||||
if renderer := fileNameRenderers["*"+ext1]; renderer != nil {
|
||||
return renderer
|
||||
}
|
||||
if basename, ok := strings.CutSuffix(basename, ext1); ok {
|
||||
ext2 := path.Ext(basename)
|
||||
if renderer := fileNameRenderers["*"+ext2+ext1]; renderer != nil {
|
||||
return renderer
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// DetectRendererType detects the markup type of the content
|
||||
func DetectRendererType(filename string, sniffedType typesniffer.SniffedType, prefetchBuf []byte) string {
|
||||
// DetectRendererTypeByPrefetch detects the markup type of the content
|
||||
func DetectRendererTypeByPrefetch(filename string, sniffedType typesniffer.SniffedType, prefetchBuf []byte) string {
|
||||
if filename != "" {
|
||||
byExt := DetectRendererTypeByFilename(filename)
|
||||
if byExt != nil {
|
||||
return byExt.Name()
|
||||
}
|
||||
}
|
||||
for _, renderer := range renderers {
|
||||
if detector, ok := renderer.(RendererContentDetector); ok && detector.CanRender(filename, sniffedType, prefetchBuf) {
|
||||
return renderer.Name()
|
||||
@@ -71,18 +97,12 @@ func DetectRendererType(filename string, sniffedType typesniffer.SniffedType, pr
|
||||
return ""
|
||||
}
|
||||
|
||||
// DetectMarkupTypeByFileName returns the possible markup format type via the filename
|
||||
func DetectMarkupTypeByFileName(filename string) string {
|
||||
if parser := GetRendererByFileName(filename); parser != nil {
|
||||
return parser.Name()
|
||||
}
|
||||
return ""
|
||||
}
|
||||
|
||||
func PreviewableExtensions() []string {
|
||||
extensions := make([]string, 0, len(extRenderers))
|
||||
for extension := range extRenderers {
|
||||
extensions = append(extensions, extension)
|
||||
exts := make([]string, 0, len(fileNameRenderers))
|
||||
for p := range fileNameRenderers {
|
||||
if s, ok := strings.CutPrefix(p, "*"); ok {
|
||||
exts = append(exts, s)
|
||||
}
|
||||
}
|
||||
return extensions
|
||||
return exts
|
||||
}
|
||||
|
||||
@@ -6,6 +6,7 @@ package setting
|
||||
import (
|
||||
"regexp"
|
||||
"strings"
|
||||
"sync"
|
||||
|
||||
"code.gitea.io/gitea/modules/log"
|
||||
"code.gitea.io/gitea/modules/util"
|
||||
@@ -43,22 +44,20 @@ var Markdown = struct {
|
||||
RenderOptionsRepoFile MarkdownRenderOptions `ini:"-"`
|
||||
|
||||
CustomURLSchemes []string `ini:"CUSTOM_URL_SCHEMES"` // Actually it is a "markup" option because it is used in "post processor"
|
||||
FileExtensions []string
|
||||
FileNamePatterns []string `ini:"-"`
|
||||
|
||||
EnableMath bool
|
||||
MathCodeBlockDetection []string
|
||||
MathCodeBlockOptions MarkdownMathCodeBlockOptions `ini:"-"`
|
||||
}{
|
||||
FileExtensions: strings.Split(".md,.markdown,.mdown,.mkd,.livemd", ","),
|
||||
EnableMath: true,
|
||||
EnableMath: true,
|
||||
}
|
||||
|
||||
// MarkupRenderer defines the external parser configured in ini
|
||||
type MarkupRenderer struct {
|
||||
Enabled bool
|
||||
MarkupName string
|
||||
Command string
|
||||
FileExtensions []string
|
||||
FilePatterns []string
|
||||
IsInputFile bool
|
||||
NeedPostProcess bool
|
||||
MarkupSanitizerRules []MarkupSanitizerRule
|
||||
@@ -77,6 +76,13 @@ type MarkupSanitizerRule struct {
|
||||
|
||||
func loadMarkupFrom(rootCfg ConfigProvider) {
|
||||
mustMapSetting(rootCfg, "markdown", &Markdown)
|
||||
|
||||
markdownFileExtensions := rootCfg.Section("markdown").Key("FILE_EXTENSIONS").Strings(",")
|
||||
if len(markdownFileExtensions) == 0 || len(markdownFileExtensions) == 1 && markdownFileExtensions[0] == "" {
|
||||
markdownFileExtensions = []string{".md", ".markdown", ".mdown", ".mkd", ".livemd"}
|
||||
}
|
||||
Markdown.FileNamePatterns = fileExtensionsToPatterns("markdown", markdownFileExtensions)
|
||||
|
||||
const none = "none"
|
||||
|
||||
const renderOptionShortIssuePattern = "short-issue-pattern"
|
||||
@@ -215,21 +221,30 @@ func createMarkupSanitizerRule(name string, sec ConfigSection) (MarkupSanitizerR
|
||||
return rule, true
|
||||
}
|
||||
|
||||
func newMarkupRenderer(name string, sec ConfigSection) {
|
||||
extensionReg := regexp.MustCompile(`\.\w`)
|
||||
var extensionReg = sync.OnceValue(func() *regexp.Regexp {
|
||||
return regexp.MustCompile(`^(\.[-\w]+)+$`)
|
||||
})
|
||||
|
||||
extensions := sec.Key("FILE_EXTENSIONS").Strings(",")
|
||||
exts := make([]string, 0, len(extensions))
|
||||
func fileExtensionsToPatterns(sectionName string, extensions []string) []string {
|
||||
patterns := make([]string, 0, len(extensions))
|
||||
for _, extension := range extensions {
|
||||
if !extensionReg.MatchString(extension) {
|
||||
log.Warn(sec.Name() + " file extension " + extension + " is invalid. Extension ignored")
|
||||
if !extensionReg().MatchString(extension) {
|
||||
log.Warn("Config section %s file extension %s is invalid. Extension ignored", sectionName, extension)
|
||||
} else {
|
||||
exts = append(exts, extension)
|
||||
patterns = append(patterns, "*"+extension)
|
||||
}
|
||||
}
|
||||
return patterns
|
||||
}
|
||||
|
||||
if len(exts) == 0 {
|
||||
log.Warn(sec.Name() + " file extension is empty, markup " + name + " ignored")
|
||||
func newMarkupRenderer(name string, sec ConfigSection) {
|
||||
if !sec.Key("ENABLED").MustBool(false) {
|
||||
return
|
||||
}
|
||||
|
||||
fileNamePatterns := fileExtensionsToPatterns(name, sec.Key("FILE_EXTENSIONS").Strings(","))
|
||||
if len(fileNamePatterns) == 0 {
|
||||
log.Warn("Config section %s file extension is empty, markup render is ignored", name)
|
||||
return
|
||||
}
|
||||
|
||||
@@ -262,11 +277,10 @@ func newMarkupRenderer(name string, sec ConfigSection) {
|
||||
}
|
||||
|
||||
ExternalMarkupRenderers = append(ExternalMarkupRenderers, &MarkupRenderer{
|
||||
Enabled: sec.Key("ENABLED").MustBool(false),
|
||||
MarkupName: name,
|
||||
FileExtensions: exts,
|
||||
Command: command,
|
||||
IsInputFile: sec.Key("IS_INPUT_FILE").MustBool(false),
|
||||
MarkupName: name,
|
||||
FilePatterns: fileNamePatterns,
|
||||
Command: command,
|
||||
IsInputFile: sec.Key("IS_INPUT_FILE").MustBool(false),
|
||||
|
||||
RenderContentMode: renderContentMode,
|
||||
RenderContentSandbox: renderContentSandbox,
|
||||
|
||||
Reference in New Issue
Block a user