diff options
Diffstat (limited to 'modules/markup/html.go')
-rw-r--r-- | modules/markup/html.go | 73 |
1 files changed, 60 insertions, 13 deletions
diff --git a/modules/markup/html.go b/modules/markup/html.go index ff5b1a76e6..f07993bc4c 100644 --- a/modules/markup/html.go +++ b/modules/markup/html.go @@ -211,6 +211,40 @@ func RenderCommitMessage( return ctx.postProcess(rawHTML) } +var commitMessageSubjectProcessors = []processor{ + fullIssuePatternProcessor, + fullSha1PatternProcessor, + linkProcessor, + mentionProcessor, + issueIndexPatternProcessor, + crossReferenceIssueIndexPatternProcessor, + sha1CurrentPatternProcessor, +} + +// RenderCommitMessageSubject will use the same logic as PostProcess and +// RenderCommitMessage, but will disable the shortLinkProcessor and +// emailAddressProcessor, will add a defaultLinkProcessor if defaultLink is set, +// which changes every text node into a link to the passed default link. +func RenderCommitMessageSubject( + rawHTML []byte, + urlPrefix, defaultLink string, + metas map[string]string, +) ([]byte, error) { + ctx := &postProcessCtx{ + metas: metas, + urlPrefix: urlPrefix, + procs: commitMessageSubjectProcessors, + } + if defaultLink != "" { + // we don't have to fear data races, because being + // commitMessageSubjectProcessors of fixed len and cap, every time we + // append something to it the slice is realloc+copied, so append always + // generates the slice ex-novo. + ctx.procs = append(ctx.procs, genDefaultLinkProcessor(defaultLink)) + } + return ctx.postProcess(rawHTML) +} + // RenderDescriptionHTML will use similar logic as PostProcess, but will // use a single special linkProcessor. func RenderDescriptionHTML( @@ -296,12 +330,17 @@ func (ctx *postProcessCtx) textNode(node *html.Node) { } } -func createLink(href, content string) *html.Node { +func createLink(href, content, class string) *html.Node { a := &html.Node{ Type: html.ElementNode, Data: atom.A.String(), Attr: []html.Attribute{{Key: "href", Val: href}}, } + + if class != "" { + a.Attr = append(a.Attr, html.Attribute{Key: "class", Val: class}) + } + text := &html.Node{ Type: html.TextNode, Data: content, @@ -311,12 +350,17 @@ func createLink(href, content string) *html.Node { return a } -func createCodeLink(href, content string) *html.Node { +func createCodeLink(href, content, class string) *html.Node { a := &html.Node{ Type: html.ElementNode, Data: atom.A.String(), Attr: []html.Attribute{{Key: "href", Val: href}}, } + + if class != "" { + a.Attr = append(a.Attr, html.Attribute{Key: "class", Val: class}) + } + text := &html.Node{ Type: html.TextNode, Data: content, @@ -364,7 +408,7 @@ func mentionProcessor(_ *postProcessCtx, node *html.Node) { } // Replace the mention with a link to the specified user. mention := node.Data[m[2]:m[3]] - replaceContent(node, m[2], m[3], createLink(util.URLJoin(setting.AppURL, mention[1:]), mention)) + replaceContent(node, m[2], m[3], createLink(util.URLJoin(setting.AppURL, mention[1:]), mention, "mention")) } func shortLinkProcessor(ctx *postProcessCtx, node *html.Node) { @@ -541,11 +585,11 @@ func fullIssuePatternProcessor(ctx *postProcessCtx, node *html.Node) { if matchOrg == ctx.metas["user"] && matchRepo == ctx.metas["repo"] { // TODO if m[4]:m[5] is not nil, then link is to a comment, // and we should indicate that in the text somehow - replaceContent(node, m[0], m[1], createLink(link, id)) + replaceContent(node, m[0], m[1], createLink(link, id, "issue")) } else { orgRepoID := matchOrg + "/" + matchRepo + id - replaceContent(node, m[0], m[1], createLink(link, orgRepoID)) + replaceContent(node, m[0], m[1], createLink(link, orgRepoID, "issue")) } } @@ -573,9 +617,9 @@ func issueIndexPatternProcessor(ctx *postProcessCtx, node *html.Node) { } else { ctx.metas["index"] = id[1:] } - link = createLink(com.Expand(ctx.metas["format"], ctx.metas), id) + link = createLink(com.Expand(ctx.metas["format"], ctx.metas), id, "issue") } else { - link = createLink(util.URLJoin(setting.AppURL, ctx.metas["user"], ctx.metas["repo"], "issues", id[1:]), id) + link = createLink(util.URLJoin(setting.AppURL, ctx.metas["user"], ctx.metas["repo"], "issues", id[1:]), id, "issue") } replaceContent(node, match[2], match[3], link) } @@ -591,7 +635,7 @@ func crossReferenceIssueIndexPatternProcessor(ctx *postProcessCtx, node *html.No repo, issue := parts[0], parts[1] replaceContent(node, m[2], m[3], - createLink(util.URLJoin(setting.AppURL, repo, "issues", issue), ref)) + createLink(util.URLJoin(setting.AppURL, repo, "issues", issue), ref, issue)) } // fullSha1PatternProcessor renders SHA containing URLs @@ -642,7 +686,7 @@ func fullSha1PatternProcessor(ctx *postProcessCtx, node *html.Node) { text += " (" + hash + ")" } - replaceContent(node, start, end, createCodeLink(urlFull, text)) + replaceContent(node, start, end, createCodeLink(urlFull, text, "commit")) } // sha1CurrentPatternProcessor renders SHA1 strings to corresponding links that @@ -672,7 +716,7 @@ func sha1CurrentPatternProcessor(ctx *postProcessCtx, node *html.Node) { } replaceContent(node, m[2], m[3], - createCodeLink(util.URLJoin(setting.AppURL, ctx.metas["user"], ctx.metas["repo"], "commit", hash), base.ShortSha(hash))) + createCodeLink(util.URLJoin(setting.AppURL, ctx.metas["user"], ctx.metas["repo"], "commit", hash), base.ShortSha(hash), "commit")) } // emailAddressProcessor replaces raw email addresses with a mailto: link. @@ -682,7 +726,7 @@ func emailAddressProcessor(ctx *postProcessCtx, node *html.Node) { return } mail := node.Data[m[2]:m[3]] - replaceContent(node, m[2], m[3], createLink("mailto:"+mail, mail)) + replaceContent(node, m[2], m[3], createLink("mailto:"+mail, mail, "mailto")) } // linkProcessor creates links for any HTTP or HTTPS URL not captured by @@ -693,7 +737,7 @@ func linkProcessor(ctx *postProcessCtx, node *html.Node) { return } uri := node.Data[m[0]:m[1]] - replaceContent(node, m[0], m[1], createLink(uri, uri)) + replaceContent(node, m[0], m[1], createLink(uri, uri, "link")) } func genDefaultLinkProcessor(defaultLink string) processor { @@ -707,7 +751,10 @@ func genDefaultLinkProcessor(defaultLink string) processor { node.Type = html.ElementNode node.Data = "a" node.DataAtom = atom.A - node.Attr = []html.Attribute{{Key: "href", Val: defaultLink}} + node.Attr = []html.Attribute{ + {Key: "href", Val: defaultLink}, + {Key: "class", Val: "default-link"}, + } node.FirstChild, node.LastChild = ch, ch } } |