gettext 3.3.6 → 3.4.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (116) hide show
  1. checksums.yaml +4 -4
  2. data/Rakefile +4 -0
  3. data/doc/text/news.md +58 -0
  4. data/gettext.gemspec +4 -3
  5. data/lib/gettext/mo.rb +7 -5
  6. data/lib/gettext/tools/msginit.rb +221 -50
  7. data/lib/gettext/tools/msgmerge.rb +13 -0
  8. data/lib/gettext/tools/parser/glade.rb +38 -40
  9. data/lib/gettext/tools/parser/gtk_builder_ui_definitions.rb +6 -3
  10. data/lib/gettext/tools/parser/ruby.rb +2 -2
  11. data/lib/gettext/version.rb +2 -2
  12. data/locale/bg/LC_MESSAGES/gettext.mo +0 -0
  13. data/locale/bs/LC_MESSAGES/gettext.mo +0 -0
  14. data/locale/ca/LC_MESSAGES/gettext.mo +0 -0
  15. data/locale/cs/LC_MESSAGES/gettext.mo +0 -0
  16. data/locale/de/LC_MESSAGES/gettext.mo +0 -0
  17. data/locale/el/LC_MESSAGES/gettext.mo +0 -0
  18. data/locale/eo/LC_MESSAGES/gettext.mo +0 -0
  19. data/locale/es/LC_MESSAGES/gettext.mo +0 -0
  20. data/locale/et/LC_MESSAGES/gettext.mo +0 -0
  21. data/locale/fr/LC_MESSAGES/gettext.mo +0 -0
  22. data/locale/hr/LC_MESSAGES/gettext.mo +0 -0
  23. data/locale/hu/LC_MESSAGES/gettext.mo +0 -0
  24. data/locale/it/LC_MESSAGES/gettext.mo +0 -0
  25. data/locale/ja/LC_MESSAGES/gettext.mo +0 -0
  26. data/locale/ko/LC_MESSAGES/gettext.mo +0 -0
  27. data/locale/lv/LC_MESSAGES/gettext.mo +0 -0
  28. data/locale/nb/LC_MESSAGES/gettext.mo +0 -0
  29. data/locale/nl/LC_MESSAGES/gettext.mo +0 -0
  30. data/locale/pt_BR/LC_MESSAGES/gettext.mo +0 -0
  31. data/locale/ru/LC_MESSAGES/gettext.mo +0 -0
  32. data/locale/sr/LC_MESSAGES/gettext.mo +0 -0
  33. data/locale/uk/LC_MESSAGES/gettext.mo +0 -0
  34. data/locale/vi/LC_MESSAGES/gettext.mo +0 -0
  35. data/locale/zh/LC_MESSAGES/gettext.mo +0 -0
  36. data/locale/zh_TW/LC_MESSAGES/gettext.mo +0 -0
  37. data/po/bg/gettext.edit.po +36 -554
  38. data/po/bg/gettext.po +0 -423
  39. data/po/bs/gettext.edit.po +36 -554
  40. data/po/bs/gettext.po +0 -423
  41. data/po/ca/gettext.edit.po +36 -554
  42. data/po/ca/gettext.po +0 -423
  43. data/po/cs/gettext.edit.po +36 -554
  44. data/po/cs/gettext.po +0 -423
  45. data/po/de/gettext.edit.po +36 -554
  46. data/po/de/gettext.po +0 -423
  47. data/po/el/gettext.edit.po +36 -554
  48. data/po/el/gettext.po +0 -423
  49. data/po/eo/gettext.edit.po +36 -554
  50. data/po/eo/gettext.po +0 -423
  51. data/po/es/gettext.edit.po +36 -554
  52. data/po/es/gettext.po +0 -423
  53. data/po/et/gettext.edit.po +36 -554
  54. data/po/et/gettext.po +0 -423
  55. data/po/fr/gettext.edit.po +36 -554
  56. data/po/fr/gettext.po +0 -423
  57. data/po/gettext.pot +37 -619
  58. data/po/hr/gettext.edit.po +36 -554
  59. data/po/hr/gettext.po +0 -423
  60. data/po/hu/gettext.edit.po +36 -554
  61. data/po/hu/gettext.po +0 -423
  62. data/po/it/gettext.edit.po +36 -554
  63. data/po/it/gettext.po +0 -423
  64. data/po/ja/gettext.edit.po +36 -554
  65. data/po/ja/gettext.po +0 -423
  66. data/po/ko/gettext.edit.po +36 -554
  67. data/po/ko/gettext.po +0 -423
  68. data/po/lv/gettext.edit.po +36 -554
  69. data/po/lv/gettext.po +0 -423
  70. data/po/nb/gettext.edit.po +36 -554
  71. data/po/nb/gettext.po +0 -423
  72. data/po/nl/gettext.edit.po +36 -554
  73. data/po/nl/gettext.po +0 -423
  74. data/po/pt_BR/gettext.edit.po +36 -554
  75. data/po/pt_BR/gettext.po +0 -423
  76. data/po/ru/gettext.edit.po +36 -554
  77. data/po/ru/gettext.po +0 -423
  78. data/po/sr/gettext.edit.po +36 -554
  79. data/po/sr/gettext.po +0 -423
  80. data/po/sv/gettext.edit.po +34 -555
  81. data/po/sv/gettext.po +0 -423
  82. data/po/uk/gettext.edit.po +36 -554
  83. data/po/uk/gettext.po +0 -423
  84. data/po/vi/gettext.edit.po +36 -554
  85. data/po/vi/gettext.po +0 -423
  86. data/po/zh/gettext.edit.po +36 -554
  87. data/po/zh/gettext.po +0 -423
  88. data/po/zh_TW/gettext.edit.po +36 -554
  89. data/po/zh_TW/gettext.po +0 -423
  90. data/test/fixtures/_.rb +1 -1
  91. data/test/fixtures/{gladeparser.glade → glade/2.glade} +0 -0
  92. data/test/fixtures/glade/3.glade +63 -0
  93. data/test/fixtures/multi_text_domain.rb +12 -12
  94. data/test/fixtures/np_.rb +1 -1
  95. data/test/fixtures/ns_.rb +1 -1
  96. data/test/fixtures/p_.rb +1 -1
  97. data/test/fixtures/ruby/{percent_i.rb → percent_lower_i.rb} +0 -0
  98. data/test/fixtures/ruby/{percent_w.rb → percent_lower_w.rb} +0 -0
  99. data/test/fixtures/ruby/{percent_I.rb → percent_upper_i.rb} +0 -0
  100. data/test/fixtures/ruby/{percent_W.rb → percent_upper_w.rb} +0 -0
  101. data/test/fixtures/s_.rb +1 -1
  102. data/test/fixtures/simple.rb +1 -1
  103. data/test/fixtures/upper_nn_.rb +77 -0
  104. data/test/po/_.pot +20 -4
  105. data/test/po/ja/_.edit.po +24 -0
  106. data/test/po/np_.pot +8 -5
  107. data/test/po/ns_.pot +6 -4
  108. data/test/po/p_.pot +3 -3
  109. data/test/po/s_.pot +6 -4
  110. data/test/test_parser.rb +35 -17
  111. data/test/tools/parser/test_glade.rb +91 -0
  112. data/test/tools/parser/test_gtk_builder_ui_definitions.rb +19 -1
  113. data/test/tools/parser/test_ruby.rb +4 -4
  114. data/test/tools/test_msginit.rb +82 -3
  115. data/test/tools/test_msgmerge.rb +34 -0
  116. metadata +28 -11
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: e644842bf5dd767497cbcb53f5ad651604e709bc4a484e460bfd8d2e1040b1cd
4
- data.tar.gz: 798048056cf35d51a238480448139a4316fab5decaa26f161add7c1cd53e91e3
3
+ metadata.gz: f1f67074e07acb7cb3db6bb2ad8919d80a89f8da9c7e69d31ab29297178ea83f
4
+ data.tar.gz: a4f732674bdca1d8514835839368dea0650119bc1289c84cb91c9cad9ff3f480
5
5
  SHA512:
6
- metadata.gz: 81e13f5f41667f9885f27b65ad6179151b7c25fdf05e7ac49964d45827e0725fa72bc7b40a6e0a52e69a5a86f46c98f2efb36eb606796636bf407072b372ad01
7
- data.tar.gz: 887292f88d3bf9baef49bbf2af55082689b889010a1328f69ec2387b65abf346b348080b5932ac7dd3393c39d5f2a79e9d375fc48c89d28e8ba242cb54f5b95c
6
+ metadata.gz: bdf37e07ffe50e49fe9eab4854f17a84d50816e44fcf97a36d9d782dec970fe2d2be02edd5717ad477ec6752f125d7e05d7a0b8935114baa322babbec1d579e4
7
+ data.tar.gz: 30327be21a39f87162332f3487897ac6e3fcadf358b2d93e6a7658cd0ac6f22c3aca28f62feec68cedaa545561c26d136633adecf012e775bb8382c62ea026ff
data/Rakefile CHANGED
@@ -86,6 +86,10 @@ end
86
86
  xgettext_options = ["--add-comments=TRANSLATORS:"]
87
87
  GetText::Tools::Task.define do |task|
88
88
  task.spec = spec
89
+ task.files = task.files.reject do |file|
90
+ file.start_with?("samples/") or
91
+ file.start_with?("test/")
92
+ end
89
93
  task.xgettext_options.concat(xgettext_options)
90
94
  end
91
95
 
data/doc/text/news.md CHANGED
@@ -1,5 +1,63 @@
1
1
  # News
2
2
 
3
+ ## 3.4.0: 2021-08-26 {#version-3-4-0}
4
+
5
+ ### Improvements
6
+
7
+ * test: Added missing Red Datasets availability check.
8
+ [GitHub#87][Reported by Mamoru TASAKA]
9
+
10
+ ### Thanks
11
+
12
+ * Mamoru TASAKA
13
+
14
+ ## 3.3.9: 2021-08-26 {#version-3-3-9}
15
+
16
+ ### Improvements
17
+
18
+ * msginit: Made Red Datasets dependency optional.
19
+ [GitHub:red-datatools/red-datasets#105][Suggested by Mamoru TASAKA]
20
+
21
+ ### Thanks
22
+
23
+ * Mamoru TASAKA
24
+
25
+ ## 3.3.8: 2021-06-09 {#version-3-3-8}
26
+
27
+ ### Improvements
28
+
29
+ * msginit: Added support for generating plural forms with
30
+ Unicode's CLDR plural rules data.
31
+ [GitHub#85][Suggested by Michaël Hoste]
32
+
33
+ * rxgettext ui: Added support for GtkBuilder UI definitions format
34
+ with `.glade` extension.
35
+ [GitHub#74][Reported by dorle-o]
36
+
37
+ ### Fixes
38
+
39
+ * rxgettext ruby: Fixed a bug that `Nn_` isn't extracted.
40
+ [GitHub#86][Reported by Kai Ramuenke]
41
+
42
+ ### Thanks
43
+
44
+ * Kai Ramuenke
45
+
46
+ * Michaël Hoste
47
+
48
+ * dorle-o
49
+
50
+ ## 3.3.7: 2021-01-18 {#version-3-3-7}
51
+
52
+ ### Improvements
53
+
54
+ * msgmerge: Added `--no-report-warning` option.
55
+ [GitHub#81][Reported by Akim Demaille]
56
+
57
+ ### Thanks
58
+
59
+ * Akim Demaille
60
+
3
61
  ## 3.3.6: 2020-08-04 {#version-3-3-6}
4
62
 
5
63
  ### Improvements
data/gettext.gemspec CHANGED
@@ -31,11 +31,12 @@ So you can use GNU gettext tools for maintaining.
31
31
 
32
32
  s.add_runtime_dependency("locale", ">= 2.0.5")
33
33
  s.add_runtime_dependency("text", ">= 1.3.0")
34
- s.add_development_dependency("rake")
35
- s.add_development_dependency("racc")
36
- s.add_development_dependency("yard")
37
34
  s.add_development_dependency("kramdown")
35
+ s.add_development_dependency("racc")
36
+ s.add_development_dependency("rake")
37
+ s.add_development_dependency("red-datasets")
38
38
  s.add_development_dependency("test-unit")
39
39
  s.add_development_dependency("test-unit-rr")
40
+ s.add_development_dependency("yard")
40
41
  s.license = "Ruby or LGPLv3+"
41
42
  end
data/lib/gettext/mo.rb CHANGED
@@ -278,11 +278,13 @@ module GetText
278
278
 
279
279
  def load_from_file(filename)
280
280
  @filename = filename
281
- begin
282
- File.open(filename, 'rb'){|f| load_from_stream(f)}
283
- rescue => e
284
- e.set_backtrace("File: #{@filename}")
285
- raise e
281
+ File.open(filename, 'rb') do |f|
282
+ begin
283
+ load_from_stream(f)
284
+ rescue => e
285
+ e.set_backtrace(["#{filename}:#{f.lineno}"] + e.backtrace)
286
+ raise e
287
+ end
286
288
  end
287
289
  end
288
290
 
@@ -1,7 +1,7 @@
1
1
  # -*- coding: utf-8 -*-
2
2
  #
3
3
  # Copyright (C) 2012 Haruka Yoshihara <yoshihara@clear-code.com>
4
- # Copyright (C) 2012-2014 Kouhei Sutou <kou@clear-code.com>
4
+ # Copyright (C) 2012-2021 Sutou Kouhei <kou@clear-code.com>
5
5
  #
6
6
  # License: Ruby's or LGPL
7
7
  #
@@ -19,11 +19,17 @@
19
19
  # along with this program. If not, see <http://www.gnu.org/licenses/>.
20
20
 
21
21
  require "etc"
22
+ require "optparse"
23
+
24
+ begin
25
+ require "datasets"
26
+ rescue LoadError
27
+ end
28
+ require "locale/info"
29
+
22
30
  require "gettext"
23
31
  require "gettext/po_parser"
24
32
  require "gettext/tools/msgmerge"
25
- require "locale/info"
26
- require "optparse"
27
33
 
28
34
  module GetText
29
35
  module Tools
@@ -320,53 +326,8 @@ module GetText
320
326
  end
321
327
 
322
328
  def plural_forms(language)
323
- case language
324
- when "ja", "vi", "ko", /\Azh.*\z/
325
- nplural = "1"
326
- plural_expression = "0"
327
- when "en", "de", "nl", "sv", "da", "no", "fo", "es", "pt",
328
- "it", "bg", "el", "fi", "et", "he", "eo", "hu", "tr",
329
- "ca", "nb"
330
- nplural = "2"
331
- plural_expression = "n != 1"
332
- when "pt_BR", "fr"
333
- nplural = "2"
334
- plural_expression = "n>1"
335
- when "lv"
336
- nplural = "3"
337
- plural_expression = "n%10==1 && n%100!=11 ? 0 : n != 0 ? 1 : 2"
338
- when "ga"
339
- nplural = "3"
340
- plural_expression = "n==1 ? 0 : n==2 ? 1 : 2"
341
- when "ro"
342
- nplural = "3"
343
- plural_expression = "n==1 ? 0 : " +
344
- "(n==0 || (n%100 > 0 && n%100 < 20)) ? 1 : 2"
345
- when "lt", "bs"
346
- nplural = "3"
347
- plural_expression = "n%10==1 && n%100!=11 ? 0 : " +
348
- "n%10>=2 && (n%100<10 || n%100>=20) ? 1 : 2"
349
- when "ru", "uk", "sr", "hr"
350
- nplural = "3"
351
- plural_expression = "n%10==1 && n%100!=11 ? 0 : n%10>=2 && " +
352
- "n%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2"
353
- when "cs", "sk"
354
- nplural = "3"
355
- plural_expression = "(n==1) ? 0 : (n>=2 && n<=4) ? 1 : 2"
356
- when "pl"
357
- nplural = "3"
358
- plural_expression = "n==1 ? 0 : n%10>=2 && " +
359
- "n%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2"
360
- when "sl"
361
- nplural = "4"
362
- plural_expression = "n%100==1 ? 0 : n%100==2 ? 1 : n%100==3 " +
363
- "|| n%100==4 ? 2 : 3"
364
- else
365
- nplural = nil
366
- plural_expression = nil
367
- end
368
-
369
- "nplurals=#{nplural}; plural=#{plural_expression};"
329
+ converter = CLDRPluralsConverter.new(language)
330
+ converter.convert
370
331
  end
371
332
 
372
333
  DESCRIPTION_TITLE = /^SOME DESCRIPTIVE TITLE\.$/
@@ -408,6 +369,216 @@ module GetText
408
369
  def year
409
370
  now.year
410
371
  end
372
+
373
+ class CLDRPluralsConverter
374
+ def initialize(language)
375
+ @language = language
376
+
377
+ end
378
+
379
+ def convert
380
+ n_plurals = nil
381
+ expression = nil
382
+ if defined?(Datasets::CLDRPlurals)
383
+ plurals = Datasets::CLDRPlurals.new
384
+ plurals.each do |locale|
385
+ next unless locale.name == @language
386
+ n_plurals, expression = convert_plural_rules(locale.rules)
387
+ break
388
+ end
389
+ end
390
+ "nplurals=#{n_plurals}; plural=#{expression};"
391
+ end
392
+
393
+ private
394
+ def convert_plural_rules(rules)
395
+ n_plurals = 1
396
+ conditions = []
397
+ order = [
398
+ "one",
399
+ "zero",
400
+ "two",
401
+ "few",
402
+ "many",
403
+ "other",
404
+ ]
405
+ rules = rules.reject do |rule|
406
+ rule.integer_samples.nil?
407
+ end
408
+ rules = rules.sort_by do |rule|
409
+ order.index(rule.count)
410
+ end
411
+ rules[0..-2].each do |rule|
412
+ next if rule.condition.nil?
413
+ condition = convert_plural_condition(rule.condition)
414
+ next if condition.nil?
415
+ next if condition == false
416
+ n_plurals += 1
417
+ conditions << condition
418
+ end
419
+ expression = ""
420
+ case conditions.size
421
+ when 0
422
+ expression << "0"
423
+ when 1
424
+ condition = conditions[0]
425
+ case condition
426
+ when "(n == 1)"
427
+ expression << "n != 1"
428
+ when "(n <= 1)"
429
+ expression << "n > 1"
430
+ else
431
+ expression << "#{condition} ? 1 : 0"
432
+ end
433
+ else
434
+ (conditions.size + 1).times do |i|
435
+ if i == conditions.size
436
+ expression << i.to_s
437
+ else
438
+ condition = conditions[i]
439
+ expression << "#{condition} ? #{i} : "
440
+ end
441
+ end
442
+ end
443
+ [n_plurals, expression]
444
+ end
445
+
446
+ def convert_plural_condition(condition)
447
+ case condition[0]
448
+ when :and
449
+ gettext_condition = nil
450
+ condition[1..-1].each do |sub_condition|
451
+ sub_gettext_condition = convert_plural_condition(sub_condition)
452
+ case sub_gettext_condition
453
+ when String
454
+ if gettext_condition.is_a?(String)
455
+ gettext_condition << " && #{sub_gettext_condition}"
456
+ else
457
+ gettext_condition = sub_gettext_condition
458
+ end
459
+ when TrueClass
460
+ unless gettext_condition.is_a?(String)
461
+ gettext_condition = true
462
+ end
463
+ when FalseClass
464
+ return false
465
+ else
466
+ raise "unknown value #{sub_gettext_condition.inspect}"
467
+ end
468
+ end
469
+ gettext_condition
470
+ when :or
471
+ gettext_condition = false
472
+ condition[1..-1].each do |sub_condition|
473
+ sub_gettext_condition = convert_plural_condition(sub_condition)
474
+ case sub_gettext_condition
475
+ when String
476
+ if gettext_condition.is_a?(String)
477
+ gettext_condition << " || #{sub_gettext_condition}"
478
+ else
479
+ gettext_condition = sub_gettext_condition
480
+ end
481
+ when TrueClass
482
+ return true
483
+ when FalseClass
484
+ else
485
+ raise "unknown value #{sub_gettext_condition.inspect}"
486
+ end
487
+ end
488
+ gettext_condition
489
+ when :equal
490
+ left = convert_plural_condition(condition[1])
491
+ right = condition[2]
492
+ case left
493
+ when String
494
+ right = compact_equal_values(right)
495
+ gettext_conditions = right.collect do |right_value|
496
+ case right_value
497
+ when Range
498
+ if right_value.begin.zero?
499
+ "(#{left} <= #{right_value.end})"
500
+ else
501
+ "(#{left} >= #{right_value.begin} && " +
502
+ "#{left} <= #{right_value.end})"
503
+ end
504
+ else
505
+ "(#{left} == #{right_value})"
506
+ end
507
+ end
508
+ if gettext_conditions.size == 1
509
+ gettext_conditions[0]
510
+ else
511
+ gettext_conditions.join(" || ")
512
+ end
513
+ when 0
514
+ if right.include?(0)
515
+ true
516
+ else
517
+ false
518
+ end
519
+ else
520
+ false
521
+ end
522
+ when :not_equal
523
+ left = convert_plural_condition(condition[1])
524
+ right = condition[2]
525
+ case left
526
+ when String
527
+ right = compact_equal_values(right)
528
+ gettext_conditions = right.collect do |right_value|
529
+ case right_value
530
+ when Range
531
+ "(#{left} < #{right_value.begin} || " +
532
+ "#{left} > #{right_value.end})"
533
+ else
534
+ "(#{left} != #{right_value})"
535
+ end
536
+ end
537
+ if gettext_conditions.size == 1
538
+ gettext_conditions[0]
539
+ else
540
+ gettext_conditions = gettext_conditions.collect do |gettext_condition|
541
+ "(#{gettext_condition})"
542
+ end
543
+ gettext_conditions.join(" && ")
544
+ end
545
+ when 0
546
+ if right.include?(0)
547
+ false
548
+ else
549
+ true
550
+ end
551
+ else
552
+ false
553
+ end
554
+ when :mod
555
+ left = convert_plural_condition(condition[1])
556
+ right = condition[2]
557
+ case left
558
+ when "n"
559
+ "(n % #{right})"
560
+ else
561
+ false
562
+ end
563
+ when "n", "i"
564
+ "n"
565
+ when "v", "w"
566
+ 0
567
+ when "f", "t", "c", "e"
568
+ false
569
+ else
570
+ raise "unknown operator: #{condition[0].inspect}"
571
+ end
572
+ end
573
+
574
+ def compact_equal_values(values)
575
+ if values == [0, 1]
576
+ [0..1]
577
+ else
578
+ values
579
+ end
580
+ end
581
+ end
411
582
  end
412
583
  end
413
584
  end
@@ -49,6 +49,7 @@ module GetText
49
49
  config.parse(command_line)
50
50
 
51
51
  parser = POParser.new
52
+ parser.report_warning = config.report_warning?
52
53
  parser.ignore_fuzzy = false
53
54
  definition_po = PO.new
54
55
  reference_pot = PO.new
@@ -313,6 +314,7 @@ module GetText
313
314
  }
314
315
  @enable_fuzzy_matching = true
315
316
  @update = nil
317
+ @report_warning = true
316
318
  @output_obsolete_entries = true
317
319
  @backup = ENV["VERSION_CONTROL"]
318
320
  @suffix = ENV["SIMPLE_BACKUP_SUFFIX"] || "~"
@@ -337,6 +339,12 @@ module GetText
337
339
  @enable_fuzzy_matching
338
340
  end
339
341
 
342
+ # @return [Bool] true if reporting warning is enabled,
343
+ # false otherwise.
344
+ def report_warning?
345
+ @report_warning
346
+ end
347
+
340
348
  # @return [Bool] true if outputting obsolete entries is
341
349
  # enabled, false otherwise.
342
350
  def output_obsolete_entries?
@@ -422,6 +430,11 @@ module GetText
422
430
  @enable_fuzzy_matching = boolean
423
431
  end
424
432
 
433
+ parser.on("--no-report-warning",
434
+ _("Don't report warning messages")) do |report_warning|
435
+ @report_warning = report_warning
436
+ end
437
+
425
438
  parser.on("--no-obsolete-entries",
426
439
  _("Don't output obsolete entries")) do |boolean|
427
440
  @output_obsolete_entries = boolean