diff options
author | David E. Wheeler <david@justatheory.com> | 2018-06-04 13:47:03 -0400 |
---|---|---|
committer | Bjørn Erik Pedersen <bjorn.erik.pedersen@gmail.com> | 2018-06-04 20:47:03 +0300 |
commit | 019bd5576be87c9f06b6a928ede1a5e78677f7b3 (patch) | |
tree | 2eba3a897b200a127ccd5e2e952551e03a9c5c89 | |
parent | c3115292a7f2d2623cb45054a361e997ad9330c9 (diff) |
tpl/strings: strings.RuneCount
-rw-r--r-- | docs/content/en/functions/strings.RuneCount.md | 28 | ||||
-rw-r--r-- | docs/data/docs.json | 20 | ||||
-rw-r--r-- | tpl/strings/init.go | 5 | ||||
-rw-r--r-- | tpl/strings/strings.go | 9 | ||||
-rw-r--r-- | tpl/strings/strings_test.go | 27 |
5 files changed, 88 insertions, 1 deletions
diff --git a/docs/content/en/functions/strings.RuneCount.md b/docs/content/en/functions/strings.RuneCount.md new file mode 100644 index 000000000..63012ab39 --- /dev/null +++ b/docs/content/en/functions/strings.RuneCount.md @@ -0,0 +1,28 @@ +--- +title: strings.RuneCount +description: Determines the number of runes in a string. +godocref: +date: 2018-06-01 +publishdate: 2018-06-01 +lastmod: 2018-06-01 +categories: [functions] +menu: + docs: + parent: "functions" +keywords: [counting, character count, length, rune length, rune count] +signature: ["strings.RuneCount INPUT"] +workson: [] +hugoversion: +relatedfuncs: ["len", "countrunes"] +deprecated: false +aliases: [] +--- + +In contrast with `strings.CountRunes` function, which strips HTML and whitespace before counting runes, `strings.RuneCount` simply counts all the runes in a string. It relies on the Go [`utf8.RuneCountInString`] function. + +``` +{{ "Hello, 世界" | strings.RuneCount }} +<!-- outputs a content length of 9 runes. --> +``` + +[`utf8.RuneCount`]: https://golang.org/pkg/unicode/utf8/#RuneCount
\ No newline at end of file diff --git a/docs/data/docs.json b/docs/data/docs.json index 4eddf8eae..3020a21f2 100644 --- a/docs/data/docs.json +++ b/docs/data/docs.json @@ -3146,7 +3146,25 @@ "Aliases": [ "countrunes" ], - "Examples": [] + "Examples": [ + [ + "{{ \"Hello, 世界\" | countrunes }}", + "8" + ] + ] + }, + "RuneCount": { + "Description": "RuneCount returns the number of runes in s", + "Args": [ + "s" + ], + "Aliases": [], + "Examples": [ + [ + "{{ \"Hello, 世界\" | strings.RuneCount }}", + "9" + ] + ] }, "CountWords": { "Description": "CountWords returns the approximate word count in s.", diff --git a/tpl/strings/init.go b/tpl/strings/init.go index 883ce76d1..8ff4cf98f 100644 --- a/tpl/strings/init.go +++ b/tpl/strings/init.go @@ -41,6 +41,11 @@ func init() { [][2]string{}, ) + ns.AddMethodMapping(ctx.RuneCount, + nil, + [][2]string{}, + ) + ns.AddMethodMapping(ctx.CountWords, []string{"countwords"}, [][2]string{}, diff --git a/tpl/strings/strings.go b/tpl/strings/strings.go index d7d8f2d85..1864bb9e0 100644 --- a/tpl/strings/strings.go +++ b/tpl/strings/strings.go @@ -57,6 +57,15 @@ func (ns *Namespace) CountRunes(s interface{}) (int, error) { return counter, nil } +// RuneCount returns the number of runes in s. +func (ns *Namespace) RuneCount(s interface{}) (int, error) { + ss, err := cast.ToStringE(s) + if err != nil { + return 0, fmt.Errorf("Failed to convert content to string: %s", err) + } + return utf8.RuneCountInString(ss), nil +} + // CountWords returns the approximate word count in s. func (ns *Namespace) CountWords(s interface{}) (int, error) { ss, err := cast.ToStringE(s) diff --git a/tpl/strings/strings_test.go b/tpl/strings/strings_test.go index 69863c30d..22695ba08 100644 --- a/tpl/strings/strings_test.go +++ b/tpl/strings/strings_test.go @@ -173,6 +173,33 @@ func TestCountRunes(t *testing.T) { } } +func TestRuneCount(t *testing.T) { + t.Parallel() + + for i, test := range []struct { + s interface{} + expect interface{} + }{ + {"foo bar", 7}, + {"旁边", 2}, + {`<div class="test">旁边</div>`, 26}, + // errors + {tstNoStringer{}, false}, + } { + errMsg := fmt.Sprintf("[%d] %v", i, test.s) + + result, err := ns.RuneCount(test.s) + + if b, ok := test.expect.(bool); ok && !b { + require.Error(t, err, errMsg) + continue + } + + require.NoError(t, err, errMsg) + assert.Equal(t, test.expect, result, errMsg) + } +} + func TestCountWords(t *testing.T) { t.Parallel() |