Skip to content
This repository was archived by the owner on Dec 31, 2024. It is now read-only.

Commit 776b81b

Browse files
TATSUNO Yasuhirokazupon
authored andcommitted
⭐ new(index): Add linked message formatting (#467) by @exoego
* Add converters to link key interpolation. * Add document for linked key formatting * Add test for unknown link key modifier
1 parent fabc563 commit 776b81b

File tree

4 files changed

+69
-13
lines changed

4 files changed

+69
-13
lines changed

gitbook/en/messages.md

Lines changed: 38 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,43 @@ Output the below:
103103
<p>DIO: the world !!!!</p>
104104
```
105105

106+
### Formatting linked locale messages
107+
108+
If the language distinguish cases of character, you may need control the case of the linked locale messages.
109+
Linked messages can be formatted with modifier `@.MODIFIER:key`
110+
111+
The below modifiers are available currently.
112+
113+
* `upper`: Uppercase all characters in the linked message.
114+
* `lower`: Lowercase all characters in the linked message.
115+
116+
Locale messages the below:
117+
118+
```javascript
119+
const messages = {
120+
en: {
121+
message: {
122+
homeAddress: 'Home address',
123+
missingHomeAddress: 'Please provide @.lower:message.homeAddress'
124+
}
125+
}
126+
}
127+
```
128+
129+
```html
130+
<label>{{ $t('message.missingHomeAddress') }}</label>
131+
132+
<p class="error">{{ $t('message.missingHomeAddress') }}</p>
133+
```
134+
135+
Output the below:
136+
137+
```html
138+
<label>Home address</label>
139+
140+
<p class="error">Please provide home address</p>
141+
```
142+
106143
### Grouping by brackets
107144

108145
A translation key of linked locale message can also have the form of `@:(message.foo.bar.baz)` in which the link to another translation key is within brackets `()`.
@@ -132,4 +169,4 @@ Output the below:
132169

133170
```html
134171
<p>There's a reason, you lost, DIO.</p>
135-
```
172+
```

src/index.js

Lines changed: 15 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -31,8 +31,13 @@ const numberFormatKeys = [
3131
'localeMatcher',
3232
'formatMatcher'
3333
]
34-
const linkKeyMatcher = /(?:@:(?:[\w\-_|.]+|\([\w\-_|.]+\)))/g
34+
const linkKeyMatcher = /(?:@(?:\.[a-z]+)?:(?:[\w\-_|.]+|\([\w\-_|.]+\)))/g
35+
const linkKeyPrefixMatcher = /^@(?:\.([a-z]+))?:/
3536
const bracketsMatcher = /[()]/g
37+
const formatters = {
38+
'upper': (str) => str.toLocaleUpperCase(),
39+
'lower': (str) => str.toLocaleLowerCase()
40+
}
3641

3742
export default class VueI18n {
3843
static install: () => void
@@ -234,7 +239,7 @@ export default class VueI18n {
234239
}
235240

236241
// Check for the existence of links within the translated string
237-
if (ret.indexOf('@:') >= 0) {
242+
if (ret.indexOf('@:') >= 0 || ret.indexOf('@.') >= 0) {
238243
ret = this._link(locale, message, ret, host, interpolateMode, values, visitedLinkStack)
239244
}
240245

@@ -263,8 +268,11 @@ export default class VueI18n {
263268
continue
264269
}
265270
const link: string = matches[idx]
266-
// Remove the leading @: and the brackets
267-
const linkPlaceholder: string = link.substr(2).replace(bracketsMatcher, '')
271+
const linkKeyPrefixMatches: any = link.match(linkKeyPrefixMatcher)
272+
const [linkPrefix, formatterName] = linkKeyPrefixMatches
273+
274+
// Remove the leading @:, @.case: and the brackets
275+
const linkPlaceholder: string = link.replace(linkPrefix, '').replace(bracketsMatcher, '')
268276

269277
if (visitedLinkStack.includes(linkPlaceholder)) {
270278
if (process.env.NODE_ENV !== 'production') {
@@ -298,6 +306,9 @@ export default class VueI18n {
298306
locale, linkPlaceholder, translated, host,
299307
Array.isArray(values) ? values : [values]
300308
)
309+
if (formatters.hasOwnProperty(formatterName)) {
310+
translated = formatters[formatterName](translated)
311+
}
301312

302313
visitedLinkStack.pop()
303314

test/unit/basic.test.js

Lines changed: 12 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -29,30 +29,34 @@ describe('basic', () => {
2929
it('should translate simple link', () => {
3030
assert.equal(i18n.t('message.link'), messages.en.message.hello)
3131
})
32-
})
3332

34-
describe('linked translation', () => {
3533
it('should translate link at the end of locale', () => {
3634
assert.equal(i18n.t('message.linkEnd'), 'This is a linked translation to the world')
3735
})
38-
})
3936

40-
describe('linked translation', () => {
4137
it('should translate link within a locale', () => {
4238
assert.equal(i18n.t('message.linkWithin'), 'Isn\'t the world we live in great?')
4339
})
44-
})
4540

46-
describe('linked translation', () => {
4741
it('should translate multiple links within a locale', () => {
4842
assert.equal(i18n.t('message.linkMultiple'), 'Hello hoge!, isn\'t the world great?')
4943
})
50-
})
5144

52-
describe('linked translation', () => {
5345
it('should translate link with braces ', () => {
5446
assert.strictEqual(i18n.t('message.linkBrackets'), 'Hello hoge. Isn\'t the world great?')
5547
})
48+
49+
it('should translate link with lower-case formatting', () => {
50+
assert.strictEqual(i18n.t('message.linkCaseLower'), 'Please provide home address')
51+
})
52+
53+
it('should translate link with upper-case formatting', () => {
54+
assert.strictEqual(i18n.t('message.linkCaseUpper'), 'HOME ADDRESS')
55+
})
56+
57+
it('should translate link without formatting if modifier is not known.', () => {
58+
assert.strictEqual(i18n.t('message.linkCaseUnknown'), 'Home address')
59+
})
5660
})
5761

5862
describe('ja locale', () => {

test/unit/fixture/index.js

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,10 @@ export default {
1717
linkHyphen: '@:hyphen-hello',
1818
linkUnderscore: '@:underscore_hello',
1919
linkList: '@:message.hello: {0} {1}',
20+
linkCaseLower: 'Please provide @.lower:message.homeAddress',
21+
linkCaseUpper: '@.upper:message.homeAddress',
22+
linkCaseUnknown: '@.unknown:message.homeAddress',
23+
homeAddress: 'Home address',
2024
circular1: 'Foo @:message.circular2',
2125
circular2: 'Bar @:message.circular3',
2226
circular3: 'Buz @:message.circular1',

0 commit comments

Comments
 (0)