i18n_po_tools 0.9.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +15 -0
- data/.gitignore +34 -0
- data/Design.md +0 -0
- data/Design.ru.md +188 -0
- data/Gemfile +4 -0
- data/LICENSE +22 -0
- data/Rakefile +1 -0
- data/Readme.md +77 -0
- data/Readme.ru.md +191 -0
- data/bin/i18n-po +9 -0
- data/i18n_yml_tools.gemspec +47 -0
- data/lib/i18n_po_tools/cli.rb +171 -0
- data/lib/i18n_po_tools/core_ext/dotted_hash.rb +34 -0
- data/lib/i18n_po_tools/data/languages.yml +26 -0
- data/lib/i18n_po_tools/data/plurals.rb +116 -0
- data/lib/i18n_po_tools/formats/android_format.rb +28 -0
- data/lib/i18n_po_tools/formats/base_format.rb +57 -0
- data/lib/i18n_po_tools/formats/basic_flat_yaml_format.rb +18 -0
- data/lib/i18n_po_tools/formats/csv_format.rb +31 -0
- data/lib/i18n_po_tools/formats/ios_format.rb +17 -0
- data/lib/i18n_po_tools/formats/po_format.rb +115 -0
- data/lib/i18n_po_tools/formats/rails_yaml_format.rb +32 -0
- data/lib/i18n_po_tools/formats.rb +32 -0
- data/lib/i18n_po_tools/plural_message.rb +18 -0
- data/lib/i18n_po_tools/utils/data.rb +25 -0
- data/lib/i18n_po_tools/utils/ios_strings.rb +83 -0
- data/lib/i18n_po_tools/utils/locfile.rb +164 -0
- data/lib/i18n_po_tools/utils/po.rb +87 -0
- data/lib/i18n_po_tools/version.rb +3 -0
- data/lib/i18n_po_tools.rb +24 -0
- metadata +185 -0
checksums.yaml
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
---
|
2
|
+
!binary "U0hBMQ==":
|
3
|
+
metadata.gz: !binary |-
|
4
|
+
OTJkYTk0MTc2YjRkOWQ3OWNlZDVhNjI2ZGY4ZDNkZjk5NDc2M2IzMw==
|
5
|
+
data.tar.gz: !binary |-
|
6
|
+
OTNmMWRkY2FkZjJmZTM5YzFlNWU4OGE3ZGMwMTEwZGM3MGJjNjVjYg==
|
7
|
+
SHA512:
|
8
|
+
metadata.gz: !binary |-
|
9
|
+
Y2JiYWRkMWVlMmEzNTA3Y2E0ZjNhZWFhYTdlNDg2NjNlNTY0ODA0ZWFjMzdl
|
10
|
+
ZDY1NjdiYzE5MTM5MTc3MTE0ZWEwYTFlODFiNzA2MjM1YTBjZDU5MmEwOGFj
|
11
|
+
M2RhMzA1M2NlOTRjMjJlYzMzNTlkODFjMTEzMDliMGJkYzBiZTU=
|
12
|
+
data.tar.gz: !binary |-
|
13
|
+
MmIzMTNhN2RkY2Y3ZWI2NjdjZjJiNzdmOGJhN2I2Yjg0YzIyM2MzNTAzNDM2
|
14
|
+
OTQ4ZTRmODNiNDA5MzZlNmNhN2I3ZDg2NGY0ZTRlY2QzYjc5OGFhYzcwZTEy
|
15
|
+
ZTYwMjA3NDI0Zjc1MWNkZWFjMGQ5YTI2ZWY1ZGYyZWU1ZDQ5Y2M=
|
data/.gitignore
ADDED
@@ -0,0 +1,34 @@
|
|
1
|
+
*.gem
|
2
|
+
*.rbc
|
3
|
+
/.config
|
4
|
+
/coverage/
|
5
|
+
/InstalledFiles
|
6
|
+
/pkg/
|
7
|
+
/spec/reports/
|
8
|
+
/test/tmp/
|
9
|
+
/test/version_tmp/
|
10
|
+
/tmp/
|
11
|
+
|
12
|
+
## Specific to RubyMotion:
|
13
|
+
.dat*
|
14
|
+
.repl_history
|
15
|
+
build/
|
16
|
+
|
17
|
+
## Documentation cache and generated files:
|
18
|
+
/.yardoc/
|
19
|
+
/_yardoc/
|
20
|
+
/doc/
|
21
|
+
/rdoc/
|
22
|
+
|
23
|
+
## Environment normalisation:
|
24
|
+
/.bundle/
|
25
|
+
/lib/bundler/man/
|
26
|
+
|
27
|
+
# for a library or gem, you might want to ignore these files since the code is
|
28
|
+
# intended to run in multiple environments; otherwise, check them in:
|
29
|
+
Gemfile.lock
|
30
|
+
.ruby-version
|
31
|
+
.ruby-gemset
|
32
|
+
|
33
|
+
# unless supporting rvm < 1.11.0 or doing something fancy, ignore this:
|
34
|
+
.rvmrc
|
data/Design.md
ADDED
File without changes
|
data/Design.ru.md
ADDED
@@ -0,0 +1,188 @@
|
|
1
|
+
Почему получилось то, что получилось
|
2
|
+
------------------------------------
|
3
|
+
|
4
|
+
Проблема
|
5
|
+
========
|
6
|
+
Есть несколько проектов:
|
7
|
+
- мобильное приложение на Android
|
8
|
+
- мобильное приложение на iOS
|
9
|
+
- настольное приложение для Mac OS X
|
10
|
+
- настольное приложение для Windows
|
11
|
+
- веб-приложение на Ruby on Rails
|
12
|
+
- маркетинговые сайты на Middleman
|
13
|
+
|
14
|
+
Они используют следующие механизмы перевода:
|
15
|
+
- Android (Java properties XML) (наследие Java)
|
16
|
+
- файлы Localizable.strings для iOS и Mac OS X, так же сделали локализацию Windows через них (собственное довольно старое изобретение)
|
17
|
+
- файлы .yml (зачем еще и эти изобрели свой формат понятно, но всё равно печально) для Ruby on Rails и Middleman
|
18
|
+
|
19
|
+
Все они поддерживают несколько языков:
|
20
|
+
- русский
|
21
|
+
- английский
|
22
|
+
- польский
|
23
|
+
- французский
|
24
|
+
|
25
|
+
Команда, в основном, знает русский и английский. Причем, русский лучше.
|
26
|
+
Остальное отдается на перевод переводчикам. Они переводят с русского или английского варианта.
|
27
|
+
|
28
|
+
Переводчики обычно технически не особенно подкованны. Им нужны простые программы, чтобы сделать свою работу.
|
29
|
+
|
30
|
+
Каждая же из систем предлагает свой вариант формата файлов для перевода.
|
31
|
+
|
32
|
+
Напрямую с ними переводчикам крайне сложно и неудобно работать. Более того,
|
33
|
+
полученный перевод, скорее всего, содержит ошибки форматирования. Так же разработка идет достаточно интенсивно, нужно достаточно часто (скажем, раз в неделю) допереводить новые строки.
|
34
|
+
|
35
|
+
Так же не хотелось бы вводить дополнительных людей, которые бы стояли между переводчиками и программистами.
|
36
|
+
|
37
|
+
1. Используем одну программу для переводчиков
|
38
|
+
=============================================
|
39
|
+
Желательно, чтобы переводчики работали в программе, а не с файлами напрямую.
|
40
|
+
Так не будет синтаксических ошибок в файлах.
|
41
|
+
|
42
|
+
Желательно, чтобы программа была одна, а не несколько, чтобы иметь общую базу
|
43
|
+
переводов. Да и обучать было бы проще.
|
44
|
+
|
45
|
+
Желательно, чтобы программа была как под Windows, так и под другие ОС. Мало ли чем будут пользоваться переводчики.
|
46
|
+
|
47
|
+
2. Используем один формат
|
48
|
+
=========================
|
49
|
+
Из желания использовать одну программу приходим к решению использовать один формат для переводов. Т.к. программ, поддерживающих все и разные не найдено.
|
50
|
+
|
51
|
+
Соответственно, нужно будет обеспечить конвертацию форматов в обе стороны.
|
52
|
+
|
53
|
+
3. PO (Gettext) спасает день
|
54
|
+
============================
|
55
|
+
Формат .po довольно популярен и достаточно прост. Все найденные редакторы его поддерживают. Его так же поддерживают различные online-редакторы (при необходимости).
|
56
|
+
|
57
|
+
Как альтернатива можно было использовать .xlf .xliff Localisation Interchange File Format, но никаких преимуществ относительно .po не увидел.
|
58
|
+
|
59
|
+
Теоритических преград для портирования из необходимых исходных форматов в обе стороны нет.
|
60
|
+
|
61
|
+
Стоит отметить, что большинство форматов основаны на первичных ключах вида "main_window.options_group.first_name.hint". PO-файлы переводят фразы с одного языка на другой. При этом изначально разработчики делают перевод хотя бы на русский язык. Но этот перевод так же хотелось бы исправлять нетехническими людьми. К счастью, есть механизм в .po файле и для задачи ключей (msgctxt). Это поможет правильно сделать обратный экспорт в любом случае.
|
62
|
+
|
63
|
+
Но при изменении русского и английского текста старый перевод будет отображаться как неиспользуемый, а новая фраза как непереведенная. Такие правки лучше исправлять людьми, т.к. улучшенный исходный текст часто будет приводить и к более точному переведенному тексту.
|
64
|
+
|
65
|
+
4. Так какие же именно программы для редактирования переводов?
|
66
|
+
=================================
|
67
|
+
Проще всего в установке и использовании, бесплатный, достаточный по функционалу http://poedit.net .
|
68
|
+
Более навороченный Lokalize из проекта KDE.
|
69
|
+
Можно использовать и другие варианты при необходимости.
|
70
|
+
|
71
|
+
5. Как хранить переводы?
|
72
|
+
========================
|
73
|
+
Переводчики народ не очень технически грамотный. Научить их обращаться с Git проблематично. Поэтому можно сделать общую папку в сервисе Dropbox (или аналогичном, их тысячи).
|
74
|
+
|
75
|
+
6. Как структурировать папку переводов?
|
76
|
+
=======================================
|
77
|
+
На первом уровне шаблоны (.pot-файлы, .po-файлы без перевода) или переводы. На втором код языка, чтобы один язык можно было отдельно распространять. Затем название приложения, а уже внутри сами файлы переводов. Шаблоны на 2-х языках (рус. и англ.) в разные папки шаблонов, т.к. с них переводят. Пример:
|
78
|
+
Templates/
|
79
|
+
ru/
|
80
|
+
editor-windows/
|
81
|
+
main.pot
|
82
|
+
en/
|
83
|
+
editor-windows/
|
84
|
+
main.pot
|
85
|
+
Translations/
|
86
|
+
ru
|
87
|
+
editor-windows/
|
88
|
+
main.po //перевод с русского на русский, для исправлений текстов нетехническими людьми
|
89
|
+
en
|
90
|
+
editor-windows/
|
91
|
+
main.po //перевод с русского на английский, для исправлений текстов нетехническими людьми
|
92
|
+
fr
|
93
|
+
editor-windows/
|
94
|
+
main.po //перевод с английского на французский
|
95
|
+
sp
|
96
|
+
editor-windows/
|
97
|
+
main.po //перевод с русского на испанский
|
98
|
+
|
99
|
+
Такой вариант позволяет без конфликтов разным людям обновлять разные папки. По сути, над отдельной папкой (точнее файлом) не работает на запись более одного человека.
|
100
|
+
|
101
|
+
Это достигается односторонним потоком данных:
|
102
|
+
src --(developer)--> pot --(translator)--> po --(developer)--> src
|
103
|
+
Как исключение, если редактор, установленный у переводчика не поддерживает удобное добавление новых строк из обновленного pot-файла, то при обновлении pot-файла могут обновляться и соотв. po-файлы.
|
104
|
+
|
105
|
+
Естественно, если было бы несколько переводчиков на один язык, то пришлось бы использовать Git или другим способом координировать их работу.
|
106
|
+
|
107
|
+
7. Не ограничиваем программистов
|
108
|
+
================================
|
109
|
+
Программисты могут использовать любой удобный для их проекта формат файлов перевода. Хранить файлы у себя в проекте в любом месте и под любым именем. Иметь столько файлов переводов сколько им удобно. Одному файлу исходному будет соответствовать 1 файл pot и по кол-ву языков файлы po.
|
110
|
+
|
111
|
+
8. Как создавать файлы переводов?
|
112
|
+
=================================
|
113
|
+
Под каждый формат нужна утила конвертирования (она может быть и одна, и несколько). Нужно их или найти, или написать свои.
|
114
|
+
|
115
|
+
Разработчик у себя в проекте создает shell-скрипт или другим образом 2 задачи:
|
116
|
+
- на импорт переводов (копирование из папки Dropbox соотв. .po-файлов и конвертирование в нативный формат)
|
117
|
+
- на экспорт переводов (экспорт в .pot-формат и копирвание в папку шаблонов)
|
118
|
+
|
119
|
+
Gem 18n-po содержит библиотеку для простого написания собственных скриптов, т.к. при большом количестве исходных файлов и языков перевода появляется много однотипных задач.
|
120
|
+
|
121
|
+
Получается схема работы (пример):
|
122
|
+
- разработчик экспортирует перевод из нативного формата в файлы example.pot и example_dialogs.pot, они помещаются в папку Templates/ru/example/ в Dropbox
|
123
|
+
- переводчик на английский в редакторе открывает эти файлы, переводит и кладет файлы example.po и example_dialogs.po в папку Translations/en/example/
|
124
|
+
- разработчик example (или переводчик у которого настроен запуск) запускает конвертацию из переводов в шаблоны Templates/en/example. Аналогично и с русским языком, если его исправляли. В этот же момент для удобства можно сделать merge из pot в po файлы (если такое делается, то организационно нужно согласовать так, чтобы в это время файлы переводов этого приложения ни одним из переводчиков не обновлялись). Это шел-скрипт без параметров (для простоты запуска).
|
125
|
+
- переводчики на другие языки открывают шаблоны на русском или английском и переводят. Файлы .po кладут в папку своего языка и приложения. Если перевод уже был, то при обновлении .pot-файла редакторы сами заметят, что появились новые строки. Если редактор менее навороченный, то в п.1 при экспорте переводов нужно так же запустить утилиту из пакета gettext по слиянию переводов. При этом в .po файлах появятся непереведенне строки.
|
126
|
+
- разработчик запускает импорт переводов. Файлы из Dropbox переводятся в нативный формат и помещаются в нужные места в проекте.
|
127
|
+
|
128
|
+
9. Что делать с уже существующими переводами в нативном формате?
|
129
|
+
================================================================
|
130
|
+
Основная утила i18n-po поддерживает импорт/экспорт во все стороны. Разово пишем команды для фомирования исходных po-файлов.
|
131
|
+
|
132
|
+
10. Так как помещать новые непереведенные строки из .pot файлов в .po файлы?
|
133
|
+
============================================================================
|
134
|
+
В идеале это делает редактор. Иначе стандартный пакет для работы с файлами .po -- gettext -- содержит утилиту для этого. Через PO-редактор Catalog > Update from POT-file. Утила из gettext:
|
135
|
+
msgmerge --update example.po example.pot
|
136
|
+
|
137
|
+
11. Как конвертировать перевод в Android .xml формат из .po?
|
138
|
+
===========================================================
|
139
|
+
Пришлось свою утилу писать. Опубликована как i18n-po gem.
|
140
|
+
|
141
|
+
12. Как конвертировать перевод в .strings формат из .po?
|
142
|
+
========================================================
|
143
|
+
Пришлось свою утилу писать. Опубликована как i18n-po gem.
|
144
|
+
|
145
|
+
13. Как конвертировать перевод в .yml формат из .po?
|
146
|
+
====================================================
|
147
|
+
Пришлось свою утилу писать. Опубликована как i18n-po gem.
|
148
|
+
|
149
|
+
14. Как конвертировать перевод в .po формат из Android .xml?
|
150
|
+
===========================================================
|
151
|
+
Пришлось свою утилу писать. Опубликована как i18n-po gem.
|
152
|
+
|
153
|
+
15. Как конвертировать перевод в .po формат из .strings?
|
154
|
+
===========================================================
|
155
|
+
Пришлось свою утилу писать. Опубликована как i18n-po gem.
|
156
|
+
|
157
|
+
16. Как конвертировать перевод в .po формат из .yml?
|
158
|
+
===========================================================
|
159
|
+
Пришлось свою утилу писать. Опубликована как i18n-po gem.
|
160
|
+
|
161
|
+
17. Что из всего этого бекапить?
|
162
|
+
================================
|
163
|
+
Скрипты импорта/экспорта бекапятся как часть исходников. pot-файлы на ключах восстанавливаются из исходников. Нативные переводы восстанавливаются из .po-файлов, но не наоборот (такие утилы вне проекта, хотя и возможны). Поэтому нужно бекапить всю папку Dropbox, остальное не обязательно. Папку для бекапов можно добавлять в отдельный git-репозитарий, тогда будет бекапиться по процессу бекапа исходных текстов.
|
164
|
+
|
165
|
+
18. Нужен конвертор yml <--> po?
|
166
|
+
================================
|
167
|
+
Да. Причем нужна поддержка нескольких .yml-файлов (может генерироваться и несколько соотв. .po-файлов). И поддержка множественных форм. Конвертация в обе стороны. Проектов, которые бы удовлетворяли всем требованиям не было найдено.
|
168
|
+
|
169
|
+
19. Как добавлять новый язык?
|
170
|
+
=============================
|
171
|
+
Переводчики могут независимо из pot-файлов сделать po-файлы с переводом на новый язык. Программисты добавляют всю инфраструктуру вокруг нового языка самостоятельно: возможность его выбора, создание папок для файлов (для Apple и Android), сконвертированных из po, добавление нового языка в Locfile.
|
172
|
+
|
173
|
+
Как итог: какие сторонние программы использовались?
|
174
|
+
==================================================
|
175
|
+
1) poeditor.net
|
176
|
+
2) Dropbox
|
177
|
+
3) Gettext
|
178
|
+
4) Скрипты для автоматизации консольных команд
|
179
|
+
5) Собственный gem i18n-po для конвертаций из формата в формат и общая часть скриптов автоматизации
|
180
|
+
|
181
|
+
Что делать, если захочется статистику и прочее?
|
182
|
+
===============================================
|
183
|
+
Искать утилы для .po-файлов. Наверняка такое уже есть. Например, конвертация .po-файла в .pot:
|
184
|
+
msgfilter -i main.po -o main.pot --keep-header sed -e 's/.*//g;/^$/d'
|
185
|
+
|
186
|
+
Особенности реализации конвертации из Rails (.yml)
|
187
|
+
==================================================
|
188
|
+
Редакторы не поддерживают конструкции вида %{count}. Для plural сообщений используется автоматическая конвертация в C-format: %d <--> %{count}. В остальных случаях ничего не делается.
|
data/Gemfile
ADDED
data/LICENSE
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
The MIT License (MIT)
|
2
|
+
|
3
|
+
Copyright (c) 2014 Igor Stepin <igor_for_os@stepin.name>
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
7
|
+
in the Software without restriction, including without limitation the rights
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
10
|
+
furnished to do so, subject to the following conditions:
|
11
|
+
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
13
|
+
copies or substantial portions of the Software.
|
14
|
+
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
21
|
+
SOFTWARE.
|
22
|
+
|
data/Rakefile
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
require "bundler/gem_tasks"
|
data/Readme.md
ADDED
@@ -0,0 +1,77 @@
|
|
1
|
+
# i18n-po-tools
|
2
|
+
|
3
|
+
Utils to convert translations from source formats to PO/POT Gettex and vise versa. It allows to separate translations from development of apps.
|
4
|
+
|
5
|
+
Supported input/output formats:
|
6
|
+
* [iOS and OS X String Resources][http://developer.apple.com/documentation/Cocoa/Conceptual/LoadingResources/Strings/Strings.html] (format: ios)
|
7
|
+
* [Android String XML][http://developer.android.com/guide/topics/resources/string-resource.html] (format: android)
|
8
|
+
* [Gettext PO/POT][http://www.gnu.org/savannah-checkouts/gnu/gettext/manual/html_node/PO-Files.html] (format:po and pot)
|
9
|
+
* [Rails YAML][http://guides.rubyonrails.org/i18n.html] (format: rails-yaml)
|
10
|
+
* Basic flat YAML (format: flat-yaml)
|
11
|
+
* CVS for easy exchange with other apps (format: csv-yaml)
|
12
|
+
|
13
|
+
Direct converation between any formats supported.
|
14
|
+
|
15
|
+
About design decision you can read in the Design.txt.
|
16
|
+
|
17
|
+
Rails YAML and PO supports plural forms of messages. Example: 1 message, 2 messages.
|
18
|
+
|
19
|
+
Sorry, more info only in Russian in the Readme.re.md file.
|
20
|
+
|
21
|
+
|
22
|
+
## Installation
|
23
|
+
|
24
|
+
Add this line to your application's Gemfile:
|
25
|
+
|
26
|
+
gem 'i18n_po_tools'
|
27
|
+
|
28
|
+
And then execute:
|
29
|
+
|
30
|
+
$ bundle
|
31
|
+
|
32
|
+
Or install it yourself as:
|
33
|
+
|
34
|
+
$ gem install i18n_po_tools
|
35
|
+
|
36
|
+
|
37
|
+
## Usage
|
38
|
+
|
39
|
+
Command: i18n-po [OPTIONS]
|
40
|
+
|
41
|
+
Options
|
42
|
+
-i, --input FILENAME input filename (default STDIN)
|
43
|
+
-b, --base FILENAME base language input filename (only for po output mode)
|
44
|
+
-o, --output FILENAME output filename (default STDOUT)
|
45
|
+
-f, --from FORMAT input file format (default is autodetect by ext)
|
46
|
+
(rails_yaml, flat_yaml, po, pot, ios, android, csv)
|
47
|
+
-t, --to FORMAT output file format (default is autodetect by ext)
|
48
|
+
(rails_yaml, flat_yaml, po, pot, ios, android, csv)
|
49
|
+
-l, --language LANGUAGE input file language (only for po or rails_yaml output mode)
|
50
|
+
-h, --help help
|
51
|
+
|
52
|
+
Examples:
|
53
|
+
1) First import (generation of PO file) from Rails YAML file:
|
54
|
+
i18n-po --input ~/projects/rails_app/config/locales/devise.en.yml --language en \
|
55
|
+
--base ~/projects/rails_app/config/locales/devise.ru.yml \
|
56
|
+
--output ~/projects/translations/rails_app/devise.en.po
|
57
|
+
|
58
|
+
2) Generation of translation template (POT file) from Rails YAML file:
|
59
|
+
i18n-po --input ~/projects/rails_app/config/locales/devise.ru.yml \
|
60
|
+
--output ~/projects/translations/rails_app/devise.en.pot
|
61
|
+
|
62
|
+
3) Generation of Rails YAML file from PO file:
|
63
|
+
i18n-po --input ~/projects/translations/rails_app/devise.en.po --language en \
|
64
|
+
--output ~/projects/rails_app/config/locales/devise.en.yml
|
65
|
+
|
66
|
+
4) Translation convertation from iOS to Android format:
|
67
|
+
i18n-po --input ~/projects/ios_app/Localizable.strings \
|
68
|
+
--output ~/projects/android_app/en/strings.xml
|
69
|
+
|
70
|
+
|
71
|
+
## Contributing
|
72
|
+
|
73
|
+
1. Fork it
|
74
|
+
2. Create your feature branch (`git checkout -b my-new-feature`)
|
75
|
+
3. Commit your changes (`git commit -am 'Add some feature'`)
|
76
|
+
4. Push to the branch (`git push origin my-new-feature`)
|
77
|
+
5. Create new Pull Request
|
data/Readme.ru.md
ADDED
@@ -0,0 +1,191 @@
|
|
1
|
+
# i18n-po-tools
|
2
|
+
|
3
|
+
Утилы для конвертирования переводов из исходных форматов в PO/POT Gettex и обратно. Позволяет разделить перевод и разработку программ.
|
4
|
+
|
5
|
+
Поддерживаемые форматы (в обе стороны):
|
6
|
+
* [iOS и OS X String Resources][http://developer.apple.com/documentation/Cocoa/Conceptual/LoadingResources/Strings/Strings.html] (формат: ios)
|
7
|
+
* [Android String XML][http://developer.android.com/guide/topics/resources/string-resource.html] (формат: android)
|
8
|
+
* [Gettext PO/POT][http://www.gnu.org/savannah-checkouts/gnu/gettext/manual/html_node/PO-Files.html] (формат: po или pot)
|
9
|
+
* [Rails YAML][http://guides.rubyonrails.org/i18n.html] (формат: rails-yaml)
|
10
|
+
* Простой плоский формат YAML (формат: flat-yaml)
|
11
|
+
* CVS для упрощенного обмена с другими программами (формат: csv-yaml)
|
12
|
+
|
13
|
+
Возможна прямая конвертация между любыми поддерживаемыми форматами.
|
14
|
+
|
15
|
+
Почему проект получился таким каким получился можно прочитать в Design.ru.txt.
|
16
|
+
|
17
|
+
Rails YAML и PO поддерживают специальный вид строк для переводов, зависящих от чисел (plurals). Пример: 1 сообщение, 6 сообщений.
|
18
|
+
|
19
|
+
|
20
|
+
## Установка
|
21
|
+
|
22
|
+
Добавьте строчку в Gemfile:
|
23
|
+
|
24
|
+
gem 'i18n_po_tools'
|
25
|
+
|
26
|
+
и запустите:
|
27
|
+
|
28
|
+
$ bundle
|
29
|
+
|
30
|
+
Или установка без Gemfile:
|
31
|
+
|
32
|
+
$ gem install i18n_po_tools
|
33
|
+
|
34
|
+
|
35
|
+
## Использование
|
36
|
+
|
37
|
+
Утила: i18n-po [Опции]
|
38
|
+
|
39
|
+
Опции
|
40
|
+
-i, --input FILENAME input filename (default STDIN)
|
41
|
+
-b, --base FILENAME base language input filename (only for po output mode)
|
42
|
+
-o, --output FILENAME output filename (default STDOUT)
|
43
|
+
-f, --from FORMAT input file format (default is autodetect by ext)
|
44
|
+
(rails_yaml, flat_yaml, po, pot, ios, android, csv)
|
45
|
+
-t, --to FORMAT output file format (default is autodetect by ext)
|
46
|
+
(rails_yaml, flat_yaml, po, pot, ios, android, csv)
|
47
|
+
-l, --language LANGUAGE input file language (only for po or rails_yaml output mode)
|
48
|
+
-h, --help help
|
49
|
+
|
50
|
+
Примеры:
|
51
|
+
1) Первоначальный импорт перевода (генерация po-файла) из Rails yml-файла:
|
52
|
+
i18n-po --input ~/projects/rails_app/config/locales/devise.en.yml --language en \
|
53
|
+
--base ~/projects/rails_app/config/locales/devise.ru.yml \
|
54
|
+
--output ~/projects/translations/rails_app/devise.en.po
|
55
|
+
|
56
|
+
2) Генерация шаблона для перевода (pot-файла) из Rails yml-файла:
|
57
|
+
i18n-po --input ~/projects/rails_app/config/locales/devise.ru.yml \
|
58
|
+
--output ~/projects/translations/rails_app/devise.en.pot
|
59
|
+
|
60
|
+
3) Генерация Rails yml-файла из переведенного po-файла:
|
61
|
+
i18n-po --input ~/projects/translations/rails_app/devise.en.po --language en \
|
62
|
+
--output ~/projects/rails_app/config/locales/devise.en.yml
|
63
|
+
|
64
|
+
4) Конвертация файла перевода из iOS-формата в Android:
|
65
|
+
i18n-po --input ~/projects/ios_app/Localizable.strings \
|
66
|
+
--output ~/projects/android_app/en/strings.xml
|
67
|
+
|
68
|
+
|
69
|
+
## Как работает механизм переводов на базе i18n-po?
|
70
|
+
Системой пользуются 2 роли пользователей: переводчики и разработчики прикладных программ.
|
71
|
+
|
72
|
+
Источником данных являются .po-файлы. Файлы в приложениях -- автосгенерированы из .po-файлов.
|
73
|
+
|
74
|
+
|
75
|
+
## Со стороны переводчиков
|
76
|
+
У переводчиков есть папка в Dropbox (или аналогичном сервисе). Они открывают папку своего языка в [PO Editor](http://poedit.net) (доступен под Windows,
|
77
|
+
Mac OS X и Linux), выбирают язык для перевода и переводят.
|
78
|
+
|
79
|
+
Структура папки:
|
80
|
+
Templates/
|
81
|
+
ru/
|
82
|
+
example-app/
|
83
|
+
main.pot
|
84
|
+
en/
|
85
|
+
example-app/
|
86
|
+
main.pot
|
87
|
+
Translations/
|
88
|
+
ru/
|
89
|
+
example-app/
|
90
|
+
main.po //перевод с русского на русский, для исправлений текстов нетехническими людьми
|
91
|
+
en/
|
92
|
+
example-app/
|
93
|
+
main.po //перевод с русского на английский, для исправлений текстов нетехническими людьми
|
94
|
+
fr
|
95
|
+
example-app/
|
96
|
+
main.po //перевод с английского на французский
|
97
|
+
sp
|
98
|
+
example-app/
|
99
|
+
main.po //перевод с русского на испанский
|
100
|
+
|
101
|
+
pot-файлы -- это те же файлы .po, но без переводов.
|
102
|
+
|
103
|
+
Когда обновляется перевод в программе, то обновляются только
|
104
|
+
.pot-файлы. Уже сам редактор замечает, что они обновились и предлагает
|
105
|
+
доперевести их в .po-файле. Если редакторы без этой функции, то можно автоматически обновлять и переводы, но нужно договориться в этот момент не править переводы переводчикам.
|
106
|
+
|
107
|
+
Первоначальный импорт уже созданных переводов так же можно сделать, что уже было переведено не пропадет.
|
108
|
+
|
109
|
+
Зачем пользоваться специальным программами, если можно открыть .po-файл в текстовом редакторе?
|
110
|
+
1) Всегда корректный синтаксис файла, случайно "не сломаешь" его.
|
111
|
+
2) В редакторах, как правило, есть база перевода. Позволит аналогично переводить похожие сообщения.
|
112
|
+
3) Через некоторое время осознаешь и другие преимущества использования специализированной программы (удобный интерфейс именно для переводов, статистика и т.п.)
|
113
|
+
|
114
|
+
|
115
|
+
## Со стороны разработчиков
|
116
|
+
Готовите переводы в стандартных для своей платформы форматах.
|
117
|
+
Затем с помощью i18n-po переводите в po-файлы. Кол-во po-файлов
|
118
|
+
соответствует количеству исходных файлов.
|
119
|
+
|
120
|
+
В папке Dropbox должны присутствовать только файлы форматов .po и .pot,
|
121
|
+
чтобы не путать переводчиков.
|
122
|
+
|
123
|
+
Добавляете скрипты (или другим образом оформляете задачи) извлечения переводов
|
124
|
+
из исходников (в po-файлы) и выгрузки в исходники (в Rails yml,
|
125
|
+
iOS/MacOSX .strings, Android .xml). Используется консольная
|
126
|
+
утилитиа i18n-po. Так же они копируют новые шаблоны для переводов в Dropbox.
|
127
|
+
|
128
|
+
Рекомендуется, чтобы разработчики имели доступ к этому репозитарию и папке
|
129
|
+
Dropbox. Тогда они сами смогут обновлять шаблоны для переводов и импортировать
|
130
|
+
новые переводы.
|
131
|
+
|
132
|
+
При подготовке строк для перевода рекомендуется следовать https://techbase.kde.org/Development/Tutorials/Localization/i18n_Mistakes .
|
133
|
+
|
134
|
+
Источником переводов может быть несколько любых языков.
|
135
|
+
|
136
|
+
Первоначальное добавление языков в код своего проекта -- на стороне разработчиков, т.к. сильно зависит от программной платформы проекта и самого проекта. Для iOS, Mac OS X и Android -- это создание соотв. папок.
|
137
|
+
|
138
|
+
|
139
|
+
Замечания по сторонним программным продуктам
|
140
|
+
============================================
|
141
|
+
1) Вместо Dropbox можно использовать другие аналогичные решения. Переводчикам проще обращаться с таким решением, чем с полноценными репозитариями (например Git).
|
142
|
+
|
143
|
+
2) Вместо poedit.net можно использовать Localize из KDE http://l10n.kde.org/docs/translation-howto/gui-specialized-apps.html#lokalize . Его ставить сложнее, но по функционалу лучше.
|
144
|
+
|
145
|
+
3) Формат po-файлов позволяет использовать множество утил и программ, он известен практически всем, кто занимается переводами программ. Более того утила i18n-po поддеживает конвертацию во множество форматов, включая CSV.
|
146
|
+
|
147
|
+
|
148
|
+
Особенности реализации конвертации из Rails
|
149
|
+
===========================================
|
150
|
+
Редакторы не поддерживают конструкции вида %{count}. Для plural сообщений используется автоматическая конвертация в C-format: %d <--> %{count}. В остальных случаях ничего не делается.
|
151
|
+
|
152
|
+
|
153
|
+
## Интересные проекты
|
154
|
+
1) https://github.com/mrmans0n/localio
|
155
|
+
Сделан для перевода через гуглотаблицы. Содержит некоторые другие форматы (JSON). Из минусов: не поддерживает plurals, некоторые форматы (po). Возможны проблемы с escaping'ом.
|
156
|
+
|
157
|
+
2) https://github.com/netbe/Babelish
|
158
|
+
Основой является текстовый файл в csv формате. Соотв., нет поддержки PO и plurals.
|
159
|
+
|
160
|
+
3) https://github.com/mobiata/twine
|
161
|
+
Основой является текстовый файл в ini-подобном формате.
|
162
|
+
Поддерживает экспорт во множество форматов.
|
163
|
+
|
164
|
+
4) http://olshansk.github.io/ios_localizer/
|
165
|
+
Осуществляет автоматический перевод ios-файлов с помощью Google Translate.
|
166
|
+
Если вдруг нужно сделать плохой (зато дешевый -- $20 per 1M characters) автоматический перевод. Далее с помощью i18n-po преобразовать в любой нужный формат.
|
167
|
+
|
168
|
+
5) https://localise.biz/free/converter/yml
|
169
|
+
Online-конвертор файла в разные форматы. Пока что бесплатно. Плюсы -- множество форматов. Минус -- в любой момент может стать платным или перестать работать. Так же нет генерации po-файла из 2х исходных файлов (перевод человеческого текста, не ключей).
|
170
|
+
|
171
|
+
6) http://pology.nedohodnik.net/
|
172
|
+
Библиотека на Python для автоматизации манипуляций с po-файлами. Интересно, если писать дополнительные утилы манипуляций с переводами.
|
173
|
+
|
174
|
+
7) https://github.com/grosser/get_pomo
|
175
|
+
Если для автоматизации больше нравится Ruby, то эта библиотека поможет.
|
176
|
+
|
177
|
+
8) https://github.com/pejuko/i18n-translators-tools
|
178
|
+
Интересный, но заброшенный проект. К сожалению, вмешивается в то как Rails читает файлы переводов и в каком формате они должны быть.
|
179
|
+
|
180
|
+
9) https://github.com/airbnb/polyglot.js
|
181
|
+
Интересный проект для переводов web-части приложений. Пока что не поддерживается i18n-po, но есть все шансы.
|
182
|
+
|
183
|
+
|
184
|
+
## Contributing
|
185
|
+
|
186
|
+
1. Fork it
|
187
|
+
2. Create your feature branch (`git checkout -b my-new-feature`)
|
188
|
+
3. Commit your changes (`git commit -am 'Add some feature'`)
|
189
|
+
4. Push to the branch (`git push origin my-new-feature`)
|
190
|
+
5. Create new Pull Request
|
191
|
+
|
data/bin/i18n-po
ADDED
@@ -0,0 +1,47 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
lib = File.expand_path('../lib', __FILE__)
|
3
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
+
require 'i18n_po_tools/version'
|
5
|
+
|
6
|
+
Gem::Specification.new do |spec|
|
7
|
+
spec.name = "i18n_po_tools"
|
8
|
+
spec.version = I18nPoTools::VERSION
|
9
|
+
spec.authors = ["Igor Stepin"]
|
10
|
+
spec.email = ["igor_for_os@stepin.name"]
|
11
|
+
spec.homepage = "http://github.com/stepin/#{spec.name}"
|
12
|
+
spec.license = "MIT"
|
13
|
+
spec.summary = "Utils to convert translations from source formats to PO/POT Gettex and vise versa."
|
14
|
+
spec.description = <<EOF
|
15
|
+
Utils to convert translations from source formats to PO/POT Gettex and vise versa.
|
16
|
+
It allows to separate translations from development of apps.
|
17
|
+
|
18
|
+
Supported input/output formats:
|
19
|
+
* iOS and OS X String Resources
|
20
|
+
* Android String XML
|
21
|
+
* Gettext PO/POT
|
22
|
+
* Rails YAML
|
23
|
+
* Basic flat YAML
|
24
|
+
* CVS for easy exchange with other apps
|
25
|
+
|
26
|
+
Direct converation between any formats supported.
|
27
|
+
|
28
|
+
Rails YAML and PO supports plural forms of messages.
|
29
|
+
EOF
|
30
|
+
|
31
|
+
spec.files = `git ls-files`.split($/)
|
32
|
+
spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
|
33
|
+
spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
|
34
|
+
spec.require_paths = ["lib"]
|
35
|
+
|
36
|
+
#for Android files support
|
37
|
+
spec.add_runtime_dependency "nokogiri"
|
38
|
+
#for PO files support
|
39
|
+
spec.add_runtime_dependency "get_pomo", "= 0.9.0"
|
40
|
+
#for blank?/present?
|
41
|
+
spec.add_runtime_dependency "activesupport", "~> 4.1.6"
|
42
|
+
|
43
|
+
|
44
|
+
spec.add_development_dependency "bundler", "~> 1.3"
|
45
|
+
spec.add_development_dependency "rake"
|
46
|
+
spec.add_development_dependency "gem-release"
|
47
|
+
end
|