File: EXAMPLES

package info (click to toggle)
ruby-i18n-inflector 2.6.7-2
  • links: PTS, VCS
  • area: main
  • in suites: bookworm, forky, sid, trixie
  • size: 592 kB
  • sloc: ruby: 2,517; makefile: 3
file content (357 lines) | stat: -rw-r--r-- 10,127 bytes parent folder | download | duplicates (4)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357

== Configuring inflections

This data will be used in any further example:

=== YAML

  en:
    i18n:
      inflections:
        
        @person:
          i:          "i"
          u:          "you"
          he:         "he"
          she:        "she"
          it:         "it"
          you:        @u
        
        gender:
          m:          "male"
          f:          "female"
          n:          "neuter"
          default:    n
        
      
    welcome: "Dear @{f:Lady|m:Sir|n:You|All}!"  
    sayit:   "@person{i:I|u:You|he:He|she:She|it:It}{ }{i:am|u:are|he,she,it:is}"
    tobe:    "%{person} @person{i:am|u:are|he,she,it:is}"
  

=== Code

  I18n.backend.store_translations(:en, :i18n => { :inflections => {
    :gender => {
      :m          => 'male',
      :f          => 'female',
      :n          => 'neuter',
      :default    => :n
      },
    :@person => {
      :i          => 'i',
      :u          => 'you',
      :he         => 'he',
      :she        => 'she',
      :it         => 'it',
      :you        => :@u
      }
  }})
  
  I18n.backend.store_translations(:en, 'welcome' => 'Dear @{f:Lady|m:Sir|n:You|All}!')
  I18n.backend.store_translations(:en, 'sayit'   => '@person{i:I|u:You|he:He|she:She|it:It}{ }{i:am|u:are|he,she,it:is}')
  I18n.backend.store_translations(:en, 'tobe'    => '%{person} @person{i:am|u:are|he,she,it:is}')
  I18n.locale = :en

== Simple interpolation

When no option, it falls back to default token (n):

  I18n.translate('welcome')
  #=> "Dear You!"

When :m, it interpolates the m token's value:

  I18n.translate('welcome', :gender => :m)
  #=> "Dear Sir!"

When unknown, it falls back to default token (n):

  I18n.translate('welcome', :gender => :unknown)
  #=> "Dear You!"

When +nil+, it falls back to default token (n):

  I18n.translate('welcome', :gender => nil)
  #=> "Dear You!"

=== <tt>inflector_unknown_defaults</tt>

When <tt>:inflector_unknown_defaults</tt> is false, it falls back to free text:

  I18n.translate('welcome', :gender => :unknown, :inflector_unknown_defaults => false)
  #=> "Dear All!"

It also falls back when an inflection option is nil or empty:

  I18n.translate('welcome', :gender => nil, :inflector_unknown_defaults => false)
  #=> "Dear All!"

== Named pattern

Regular inflection option will be used if there is no strict inflection option:

  I18n.translate('sayit', :person => :i)
  #=> "I am"

Strict inflection option has precedence:

  I18n.translate('sayit', :person => :i, :@person => :u)
  #=> "You are"


Strict inflection option has precedence even if the option's value is messy:
 
  I18n.translate('sayit', :person => :i, :@person => :unknown)
  #=> " "
  
=== Using with interpolation argument

First part is interpolated using standard interpolation variable while
second part of the sentence comes from interpolation of inflection pattern.
The same option is feeding both engines.

  I18n.translate('tobe', :person => :i)
  #=> "i am"

Note funny thing. The interpolation variable +test+ takes value (+i+) from
+:person+ while option +:@person+ takes precedence when it comes to inflections.
Keep that in mind when combining regular interpolation variables with named patterns
while using the same variable for controlling both. Choose non-strict notation
for an option then.

  I18n.translate('tobe', :person => :i, :@person => :u)
  #=> "i are"

No free text in 'tobe' so the empty string is interpolated when strict kind is unknown:

  I18n.translate('tobe', :person => :i, :@person => :unknown)
  #=> "i "

== API

=== Getting kinds

Getting all known regular kinds:

  I18n.inflector.kinds
  #=> [:gender]

Getting all known strict kinds:

  I18n.inflector.strict.kinds
  #=> [:person]

Getting all known kinds for language 'pl':

  I18n.inflector.kinds(:pl)
  #=> []

=== Listing all known options

  I18n.inflector.options.known
  #=> [:inflector_cache_aware, :inflector_raises, :inflector_aliased_patterns,
  #    :inflector_unknown_defaults, :inflector_excluded_defaults]

== Real-life example for Polish language

Polish is highly inflected language. Additionally, position of a word in
a sentence is mutually coupled with meaning. That makes it extreemly
hard to create finite-state machine that would handle Polish grammar.
However, flection means that the same cores are combined with suffixes
and prefixes depending on many different kinds: gender, tense, form,
animation, declination and more. That makes Polish (and other Slavic
languages) alphabetically redundant. By interpolating common cores,
prefixes and suffixes of words we're able make our patterns compact.

=== YAML

  pl:
    are_you_sure: "@{m,f:Jesteś pew}{m:ien|f:na}{n:Na pewno}?"
    
    i18n:
      inflections:
        gender:
          f:          "rodzaj żeński"
          m:          "rodzaj męski"
          n:          "forma bezosobowa"
          masculine:  @m
          facet:      @m
          chłopak:    @m
          feminine:   @f
          pani:       @f
          kobieta:    @f
          k:          @f
          dziewczyna: @f
          impersonal: @n
          default:    n

=== Code

  # Using shorter form than listed as YAML
  
  I18n.backend.store_translations(:pl, :i18n => { :inflections => { :gender =>
                                  { :f => 'f', :m=>'m', :n=>'n', :kobieta=>:@f, :facet => :@m, :default=>:n }}})
  
  # Making use of commas makes it easy to implement DRY
  # and re-use some parts of the words that are the same in two or more phrases
  
  I18n.backend.store_translations(:pl, :are_you_sure => "@{m,f:Jesteś pew}@{m:ien|f:na}@{n:Na pewno}?")
    
  I18n.locale = :pl
  
  I18n.translate('are_you_sure', :gender => :kobieta)
  #=> "Jesteś pewna?"
    
  I18n.translate('are_you_sure', :gender => :facet)
  #=> "Jesteś pewien?"  
  
  I18n.translate('are_you_sure')
  #=> "Na pewno?"

  # It would look like that without commas:
  I18n.backend.store_translations(:pl, :are_you_sure => "@{m:Jesteś pewien|f:Jesteś pewna|n:Na pewno}?")

  # That would also work but it's less readable.
  # PS: Have you ever configured Sendmail? ;-)
  I18n.backend.store_translations(:pl, :are_you_sure => "@{n:Na|m,f:Jesteś}{ pew}{m:ie}{n}{f:a|n:o}?")

=== Complex pattern usage

  # Store needed translations
  I18n.backend.store_translations(:pl,
    :i18n => { :inflections => {
      :@gender =>
          { :f       => 'f', :m     => 'm', :n       => 'n',
            :kobieta => :@f, :facet => :@m, :default => :n },
      :@tense =>
          { :t     => 'teraz', :w       => 'przeszły', :j     => 'przyszły',
            :teraz => :@t,     :wczoraj => :@w,        :jutro => :@j,
            :default => :t }
      }})
  
  I18n.backend.store_translations(:pl,
    :msg_receive => "@gender+tense{n+w:Otrzymano|Dosta}{*+t:jesz|*+j:niesz|f+w:łaś|m+w:łeś} wiadomość")

  I18n.locale = :pl

  p I18n.translate('msg_receive', :gender => :kobieta)
  #=> "Dostajesz wiadomość"

  p I18n.translate('msg_receive', :gender => :facet)
  #=> "Dostajesz wiadomość"

  p I18n.translate('msg_receive')
  #=> "Dostajesz wiadomość"

  p I18n.translate('msg_receive', :gender => :kobieta, :tense => :wczoraj)
  #=> "Dostałaś wiadomość"

  p I18n.translate('msg_receive', :gender => :facet, :tense => :wczoraj)
  #=> "Dostałeś wiadomość"
  
  p I18n.translate('msg_receive', :tense => :jutro)
  #=> "Dostaniesz wiadomość"
  
  p I18n.translate('msg_receive', :tense => :wczoraj)
  #=> "Otrzymano wiadomość"

==== YAML for the example above

The example above may use this YAML content instead of +store_translations+:

  pl:
    msg_receive: "@gender+tense{n+w:Otrzymano|Dosta}{*+t:jesz|*+j:niesz|f+w:łaś|m+w:łeś} wiadomość"
    
    i18n:
      inflections:
        @gender:
          m:  'male'
          f:  'female'
          n:  'neuter'
          kobieta:  @f
          facet:    @m
          default:  n
        @tense:
          t:        'teraźniejszy'
          w:        'przeszły'
          j:        'przyszły'
          teraz:    @t
          wczoraj:  @w
          jutro:    @j
          default:  @t

===== Alternative for +msg_receive+ key

The +msg_receive+ might also be expressed using two infleciton keys:

  pl:
    @msg_receive_1:
      @kind:    gender+tense
      @free:    'Dosta'
      n+w:      'Otrzymano'
  
    @msg_receive_2:
      @kind:    gender+tense
      @suffix:  " wiadomość"
      m,f,n+t:  "jesz"
      m,f,n+j:  "niesz"
      f+w:      "łaś"
      m+w:      "łeś"

But then you have to change the translation call too, e.g.:

  p I18n.translate(['@msg_receive_1','@msg_receive_2'], :gender => :kobieta).join
  #=> "Dostajesz wiadomość"

The split is necessary because we have two patterns here and no way to express them
as one inflection key.

== To be or not to be

Here is the example pattern that inflects English <i>to be</i> by tense,
person and grammatical number:

  en:
    i18n:
        inflections:
          @person:
              1: first
              2: second
              3: third
              i:    :@1
              you:  :@2
              He:   :@3
              She:  :@3
              it:   :@3
          @tense:
            past:      past
            present:   present
            now:       @present
            default:   present
          @num:
            s: singular
            p: plural
            default: s
    
    to_be: >
            @num+person{s+1:I|*+2:You|s+3:%{person}|p+3:They|p+1:We}
            @num+person+tense{s+1+present:am|s+2+present:are|s+3+present:is|
            p+*+present:are|s+1,3+past:was|p+*+past:were|s+2+past:were}

And the code that prints all possible combinations:

  [:i, :you, :He, :She, :It].each do |person|
    puts  I18n.translate(:to_be, :num => :s, :person => person, :tense => :now) + "\t| " +
          I18n.translate(:to_be, :num => :s, :person => person, :tense => :past)
  end
  
  puts
  
  (1..3).each do |person|
    puts  I18n.translate(:to_be, :num => :p, :person => person, :tense => :now) + " | " +
          I18n.translate(:to_be, :num => :p, :person => person, :tense => :past)
  end

<i>to be continued…</i>