mirror of
https://github.com/mattermost/mattermost.git
synced 2026-04-15 22:12:19 -04:00
Merge consecutive text nodes when inspecting markdown (#9112)
* Fix assertion order
expected/actual were in wrong order, resulting in misleading output in
case of failing tests
* Merge consesutive markdown text nodes
This ensures that parser quirks such as "hello!" being parsed as
two separate nodes ("hello" and "!") are not exposed to code inspecting
a markdown strings.
This commit is contained in:
parent
940d0bbbc2
commit
88eef609ab
3 changed files with 57 additions and 23 deletions
|
|
@ -476,6 +476,40 @@ func ParseInlines(markdown string, ranges []Range, referenceDefinitions []*Refer
|
|||
return newInlineParser(markdown, ranges, referenceDefinitions).Parse()
|
||||
}
|
||||
|
||||
func MergeInlineText(inlines []Inline) []Inline {
|
||||
var ret []Inline
|
||||
for i, v := range inlines {
|
||||
// always add first node
|
||||
if i == 0 {
|
||||
ret = append(ret, v)
|
||||
continue
|
||||
}
|
||||
// not a text node? nothing to merge
|
||||
text, ok := v.(*Text)
|
||||
if !ok {
|
||||
ret = append(ret, v)
|
||||
continue
|
||||
}
|
||||
// previous node is not a text node? nothing to merge
|
||||
prevText, ok := ret[len(ret)-1].(*Text)
|
||||
if !ok {
|
||||
ret = append(ret, v)
|
||||
continue
|
||||
}
|
||||
// previous node is not right before this one
|
||||
if prevText.Range.End != text.Range.Position {
|
||||
ret = append(ret, v)
|
||||
continue
|
||||
}
|
||||
// we have two consecutive text nodes
|
||||
ret[len(ret)-1] = &Text{
|
||||
Text: prevText.Text + text.Text,
|
||||
Range: Range{prevText.Range.Position, text.Range.End},
|
||||
}
|
||||
}
|
||||
return ret
|
||||
}
|
||||
|
||||
func Unescape(markdown string) string {
|
||||
ret := ""
|
||||
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ func Inspect(markdown string, f func(interface{}) bool) {
|
|||
}
|
||||
switch v := block.(type) {
|
||||
case *Paragraph:
|
||||
for _, inline := range v.ParseInlines(referenceDefinitions) {
|
||||
for _, inline := range MergeInlineText(v.ParseInlines(referenceDefinitions)) {
|
||||
InspectInline(inline, func(inline Inline) bool {
|
||||
return f(inline)
|
||||
})
|
||||
|
|
|
|||
|
|
@ -22,8 +22,8 @@ func TestTextRanges(t *testing.T) {
|
|||
},
|
||||
"simple2": {
|
||||
Markdown: "hello!",
|
||||
ExpectedRanges: []Range{{0, 5}, {5, 6}},
|
||||
ExpectedValues: []string{"hello", "!"},
|
||||
ExpectedRanges: []Range{{0, 6}},
|
||||
ExpectedValues: []string{"hello!"},
|
||||
},
|
||||
"multiline": {
|
||||
Markdown: "hello world\nfoobar",
|
||||
|
|
@ -37,13 +37,13 @@ func TestTextRanges(t *testing.T) {
|
|||
},
|
||||
"notcode": {
|
||||
Markdown: "hello ` world",
|
||||
ExpectedRanges: []Range{{0, 6}, {6, 7}, {7, 13}},
|
||||
ExpectedValues: []string{"hello ", "`", " world"},
|
||||
ExpectedRanges: []Range{{0, 13}},
|
||||
ExpectedValues: []string{"hello ` world"},
|
||||
},
|
||||
"escape": {
|
||||
Markdown: "\\*hello\\*",
|
||||
ExpectedRanges: []Range{{1, 2}, {2, 7}, {8, 9}},
|
||||
ExpectedValues: []string{"*", "hello", "*"},
|
||||
ExpectedRanges: []Range{{1, 7}, {8, 9}},
|
||||
ExpectedValues: []string{"*hello", "*"},
|
||||
},
|
||||
"escapeescape": {
|
||||
Markdown: "\\\\",
|
||||
|
|
@ -52,28 +52,28 @@ func TestTextRanges(t *testing.T) {
|
|||
},
|
||||
"notescape": {
|
||||
Markdown: "foo\\x",
|
||||
ExpectedRanges: []Range{{0, 3}, {3, 4}, {4, 5}},
|
||||
ExpectedValues: []string{"foo", "\\", "x"},
|
||||
ExpectedRanges: []Range{{0, 5}},
|
||||
ExpectedValues: []string{"foo\\x"},
|
||||
},
|
||||
"notlink": {
|
||||
Markdown: "[foo",
|
||||
ExpectedRanges: []Range{{0, 1}, {1, 4}},
|
||||
ExpectedValues: []string{"[", "foo"},
|
||||
ExpectedRanges: []Range{{0, 4}},
|
||||
ExpectedValues: []string{"[foo"},
|
||||
},
|
||||
"notlinkend": {
|
||||
Markdown: "[foo]",
|
||||
ExpectedRanges: []Range{{0, 1}, {1, 4}, {4, 5}},
|
||||
ExpectedValues: []string{"[", "foo", "]"},
|
||||
ExpectedRanges: []Range{{0, 5}},
|
||||
ExpectedValues: []string{"[foo]"},
|
||||
},
|
||||
"notimage": {
|
||||
Markdown: "![foo",
|
||||
ExpectedRanges: []Range{{0, 2}, {2, 5}},
|
||||
ExpectedValues: []string{"![", "foo"},
|
||||
ExpectedRanges: []Range{{0, 5}},
|
||||
ExpectedValues: []string{"![foo"},
|
||||
},
|
||||
"notimage2": {
|
||||
Markdown: "!foo",
|
||||
ExpectedRanges: []Range{{0, 1}, {1, 4}},
|
||||
ExpectedValues: []string{"!", "foo"},
|
||||
ExpectedRanges: []Range{{0, 4}},
|
||||
ExpectedValues: []string{"!foo"},
|
||||
},
|
||||
"charref": {
|
||||
Markdown: ""test",
|
||||
|
|
@ -82,13 +82,13 @@ func TestTextRanges(t *testing.T) {
|
|||
},
|
||||
"notcharref": {
|
||||
Markdown: "& test",
|
||||
ExpectedRanges: []Range{{0, 1}, {1, 9}},
|
||||
ExpectedValues: []string{"&", "amp test"},
|
||||
ExpectedRanges: []Range{{0, 9}},
|
||||
ExpectedValues: []string{"& test"},
|
||||
},
|
||||
"notcharref2": {
|
||||
Markdown: "&mattermost;",
|
||||
ExpectedRanges: []Range{{0, 1}, {1, 12}},
|
||||
ExpectedValues: []string{"&", "mattermost;"},
|
||||
ExpectedRanges: []Range{{0, 12}},
|
||||
ExpectedValues: []string{"&mattermost;"},
|
||||
},
|
||||
} {
|
||||
t.Run(name, func(t *testing.T) {
|
||||
|
|
@ -101,8 +101,8 @@ func TestTextRanges(t *testing.T) {
|
|||
}
|
||||
return true
|
||||
})
|
||||
assert.Equal(t, ranges, tc.ExpectedRanges)
|
||||
assert.Equal(t, values, tc.ExpectedValues)
|
||||
assert.Equal(t, tc.ExpectedRanges, ranges)
|
||||
assert.Equal(t, tc.ExpectedValues, values)
|
||||
|
||||
})
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue