summaryrefslogtreecommitdiffstats
path: root/intl/l10n/docs/crosschannel
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-07 17:32:43 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-07 17:32:43 +0000
commit6bf0a5cb5034a7e684dcc3500e841785237ce2dd (patch)
treea68f146d7fa01f0134297619fbe7e33db084e0aa /intl/l10n/docs/crosschannel
parentInitial commit. (diff)
downloadthunderbird-upstream.tar.xz
thunderbird-upstream.zip
Adding upstream version 1:115.7.0.upstream/1%115.7.0upstream
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'intl/l10n/docs/crosschannel')
-rw-r--r--intl/l10n/docs/crosschannel/commits.rst33
-rw-r--r--intl/l10n/docs/crosschannel/content.rst129
-rw-r--r--intl/l10n/docs/crosschannel/index.rst88
-rw-r--r--intl/l10n/docs/crosschannel/repositories.rst14
4 files changed, 264 insertions, 0 deletions
diff --git a/intl/l10n/docs/crosschannel/commits.rst b/intl/l10n/docs/crosschannel/commits.rst
new file mode 100644
index 0000000000..955baf734f
--- /dev/null
+++ b/intl/l10n/docs/crosschannel/commits.rst
@@ -0,0 +1,33 @@
+Commits and Metadata
+====================
+
+When creating the commit for a particular revision, we need to find the
+revisions on the other branches of cross-channel to unify the created
+content with.
+
+To do so, the cross-channel algorithm keeps track of metadata associated with
+a revision in the target repository. This metadata is stored in the commit
+message:
+
+.. code-block:: bash
+
+ X-Channel-Repo: mozilla-central
+ X-Channel-Converted-Revision: af4a1de0a11cb3afbb7e50bcdd0919f56c23959a
+ X-Channel-Repo: releases/mozilla-beta
+ X-Channel-Revision: 65fb3f6bce94f8696e1571c2d48104dbdc0b31e2
+ X-Channel-Repo: releases/mozilla-release
+ X-Channel-Revision: 1c5bf69f887359645f1c3df4de0d0e3caf957e59
+ X-Channel-Repo: releases/mozilla-esr68
+ X-Channel-Revision: 4cbbc30e1ebc3254ec74dc041aff128c81220507
+
+This metadata is appended to the original commit message when committing.
+For each branch in the cross-channel configuration we have the name and
+a revision. The revision that's currently converted is explicitly highlighted
+by the ``-Converted-`` marker. On hg.mozilla.org, those revisions are also
+marked up as links, so one can navigate from the converted changeset to the
+original patch.
+
+When starting the update for an incremental graph from the previous section,
+the metadata is read from the target repository, and the data for the
+currently converted branch is updated for each commit. Each revision in
+this metadata then goes into the algorithm to create the unified content.
diff --git a/intl/l10n/docs/crosschannel/content.rst b/intl/l10n/docs/crosschannel/content.rst
new file mode 100644
index 0000000000..01f5e1ab66
--- /dev/null
+++ b/intl/l10n/docs/crosschannel/content.rst
@@ -0,0 +1,129 @@
+=====================
+Cross-channel Content
+=====================
+
+When creating the actual content, there's a number of questions to answer.
+
+#. Where to take content from?
+#. Which content to take?
+#. Where to put the content?
+#. What to put into each file?
+
+Content Sources
+---------------
+
+The content of each revision in ``gecko-strings`` corresponds to a given
+revision in each original repository. For example, we could have
+
++------------------+--------------+
+| Repository | Revision |
++==================+==============+
+| mozilla-central | 4c92802939c1 |
++------------------+--------------+
+| mozilla-beta | ace4081e8200 |
++------------------+--------------+
+| mozilla-release | 2cf08fbb92b2 |
++------------------+--------------+
+| mozilla-esr68 | 2cf9e0c91d51 |
++------------------+--------------+
+| comm-central | 3f3fc2c0d804 |
++------------------+--------------+
+| comm-beta | f95a6f4408a3 |
++------------------+--------------+
+| comm-release | dc2694f035fa |
++------------------+--------------+
+| comm-esr68 | d05d4d87d25c |
++------------------+--------------+
+
+The assumption is that there's no content that's shared between ``mozilla-*`` and
+``comm-*``, so we can just convert one repository and its branches at a time.
+
+Covered Content
+---------------
+
+Which content is included in ``gecko-strings`` is
+controlled by the project configurations of each product, on each branch.
+Currently, those are :file:`browser/locales/l10n.toml` and
+:file:`mobile/android/locales/l10n.toml` in ``mozilla-central``.
+
+Created Content Structure
+-------------------------
+
+The created content is laid out in the directory in the same structure as
+the files in ``l10n-central``. The localizable files end up like this:
+
+.. code-block::
+
+ browser/
+ browser/
+ browser.ftl
+ chrome/
+ browser.properties
+ toolkit/
+ toolkit/
+ about/aboutAbout.ftl
+
+This matches the file locations in ``mozilla-central`` with the
+:file:`locales/en-US` part dropped.
+
+The project configuration files are also converted and added to the
+created file structure. As they're commonly in the :file:`locales` folder
+which we strip, they're added to the dedicated :file:`_configs` folder.
+
+.. code-block:: bash
+
+ $ ls _configs
+ browser.toml devtools-client.toml devtools-shared.toml
+ mobile-android.toml toolkit.toml
+
+
+L10n File Contents
+------------------
+
+Let's assume we have a file to localize in several revisions with different
+content.
+
+== ======= ==== =======
+ID central beta release
+== ======= ==== =======
+a one one one
+b two two
+c three
+d four old old
+== ======= ==== =======
+
+The algorithm then creates content, taking localizable values from the left-most
+branch, where *central* overrides *beta*, and *beta* overrides *release*. This
+creates content as follows:
+
+== =======
+ID content
+== =======
+a one
+b two
+c three
+d four
+== =======
+
+If a file doesn't exist in one of the revisions, that revision is dropped
+from the content generation for this particular file.
+
+.. note::
+
+ The example of the forth string here highlights the impact that changing
+ an existing string has. We ship one translation of *four* to central,
+ beta, and release. That's only a good idea if it doesn't matter which of the
+ two versions of the English copy got translated.
+
+Project configurations
+----------------------
+
+The TOML files for project configuration are processed, but not unified
+across branches at this point.
+
+.. note::
+
+ The content of the ``-central`` branch determines what's localized
+ from ``gecko-strings``. Thus that TOML file needs to include all
+ directories across all branches for now. Removing entries requires
+ that the content is obsolete on all branches in cross-channel.
diff --git a/intl/l10n/docs/crosschannel/index.rst b/intl/l10n/docs/crosschannel/index.rst
new file mode 100644
index 0000000000..faa28d6157
--- /dev/null
+++ b/intl/l10n/docs/crosschannel/index.rst
@@ -0,0 +1,88 @@
+=============
+Cross-channel
+=============
+
+Firefox is localized with a process nick-named *cross-channel*. This document
+explains both the general idea as well as some technical details of that
+process. The gist of it is this:
+
+ We use one localization for all release channels.
+
+There's a number of upsides to that:
+
+* Localizers maintain a single source of truth. Localizers can work on Nightly,
+ while updating Beta, Developer Edition or even Release and ESR.
+* Localizers can work on strings at their timing.
+* Uplifting string changes has less of an impact on the localization toolchain,
+ and their impact can be evaluated case by case.
+
+So the problem at hand is to have one localization source
+and use that to build 5 different versions of Firefox. The goal is for that
+localization to be as complete as possible for each version. While we do
+allow for partial localizations, we don't want to enforce partial translations
+on any version.
+
+The process to tackle these follows these steps:
+
+* Create resource to localize, ``gecko-strings``.
+
+ * Review updates to that resource in *quarantine*.
+ * Expose a known good state of that resource to localizers.
+
+* The actual localization work happens in Pontoon.
+* Write localizations back to ``l10n-central``.
+* Get localizations into the builds.
+
+.. digraph:: full_tree
+
+ graph [ rankdir=LR ];
+ "m-c" -> "quarantine";
+ "m-b" -> "quarantine";
+ "m-r" -> "quarantine";
+ "c-c" -> "quarantine";
+ "c-b" -> "quarantine";
+ "c-r" -> "quarantine";
+ "quarantine" -> "gecko-strings";
+ "gecko-strings" -> "Pontoon";
+ "Pontoon" -> "l10n-central";
+ "l10n-central" -> "Nightly";
+ "l10n-central" -> "Beta";
+ "l10n-central" -> "Firefox";
+ "l10n-central" -> "Daily";
+ "l10n-central" -> "Thunderbird";
+ {
+ rank=same;
+ "quarantine";
+ "gecko-strings";
+ }
+
+.. note::
+
+ The concept behind the quarantine in the process above is to
+ protect localizers from churn on strings that have technical
+ problems. Examples like that could be missing localization notes
+ or copy that should be improved.
+
+The resource to localize is a Mercurial repository, unifying
+all strings to localize for all covered products and branches. Each revision
+of this repository holds all the strings for a particular point in time.
+
+There's three aspects that we'll want to unify here.
+
+#. Create a version history that allows the localization team
+ to learn where strings in the generated repository are coming from.
+#. Unify the content across different branches for a single app.
+#. Unify different apps, coming from different repositories.
+
+The last item is the easiest, as ``mozilla-*`` and ``comm-*`` don't share
+code or history. Thus, they're converted individually to disjunct directories
+and files in the target repository, and the Mercurial history of each is interleaved
+in the target history. When parents are needed for one repository, they're
+rebased over the commits for the other.
+
+.. toctree::
+ :maxdepth: 1
+
+ commits
+ content
+ repositories
diff --git a/intl/l10n/docs/crosschannel/repositories.rst b/intl/l10n/docs/crosschannel/repositories.rst
new file mode 100644
index 0000000000..8461b32fbd
--- /dev/null
+++ b/intl/l10n/docs/crosschannel/repositories.rst
@@ -0,0 +1,14 @@
+gecko-strings and Quarantine
+============================
+
+The actual generation is currently done via `taskcluster cron <https://treeherder.mozilla.org/jobs?repo=mozilla-central&searchStr=cross-channel>`_.
+The state that is good to use by localizers at large is published at
+https://hg.mozilla.org/l10n/gecko-strings/.
+
+The L10n team is doing a :ref:`review step <exposure-in-gecko-strings>` before publishing the strings, and while
+that is ongoing, the intermediate state is published to
+https://hg.mozilla.org/l10n/gecko-strings-quarantine/.
+
+The code is in https://hg.mozilla.org/mozilla-central/file/tip/python/l10n/mozxchannel/,
+supported as a mach subcommand in https://hg.mozilla.org/mozilla-central/file/tip/tools/compare-locales/mach_commands.py,
+as a taskcluster kind in https://hg.mozilla.org/mozilla-central/file/tip/taskcluster/ci/l10n-cross-channel, and scheduled in cron in https://hg.mozilla.org/mozilla-central/file/tip/.cron.yml.