From f6244f207c328e330a5a359e42485ad914b91b13 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Va=CC=81clav=20Slavi=CC=81k?= Date: Wed, 1 Nov 2023 16:41:15 +0100 Subject: [PATCH 1/4] Add OTA build script --- scripts/build-ota-translations.sh | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) create mode 100755 scripts/build-ota-translations.sh diff --git a/scripts/build-ota-translations.sh b/scripts/build-ota-translations.sh new file mode 100755 index 0000000000..5bf47be880 --- /dev/null +++ b/scripts/build-ota-translations.sh @@ -0,0 +1,28 @@ +#!/bin/bash +set -e + +DESTDIR="ota-update-$$" +rm -rf "$DESTDIR" +mkdir -p "$DESTDIR" +function finish { + rm -rf "$DESTDIR" +} +trap finish EXIT + +# compile PO files, taking care to make them reproducible, i.e. not change if the actual +# translations didn't change: +for po in locales/*.po ; do + mo="$(basename "$po" .po).mo" + mogz="$mo.gz" + printf "%-30s" "$po" + + sed -e 's/^"PO-Revision-Date: .*/"PO-Revision-Date: \\n"/g' "$po" | msgfmt -c -o "$DESTDIR/$mo" - + gzip --no-name -9 "$DESTDIR/$mo" + + size=$(ls -ks "$DESTDIR/$mogz" | cut -d' ' -f1) + printf "%'3d kB %s\n" "$size" "$(cd $DESTDIR && md5sum $mogz)" +done + +# create a tarball of all updates: +tar -C "$DESTDIR" -cf ota-update.tar . + From 0f13c8f2ed4d718f1ff214d44eafda82e82539aa Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Va=CC=81clav=20Slavi=CC=81k?= Date: Wed, 1 Nov 2023 16:41:27 +0100 Subject: [PATCH 2/4] Add GHA workflow to build OTA updates --- .github/workflows/build-ota-updates.yml | 36 +++++++++++++++++++++++++ 1 file changed, 36 insertions(+) create mode 100644 .github/workflows/build-ota-updates.yml diff --git a/.github/workflows/build-ota-updates.yml b/.github/workflows/build-ota-updates.yml new file mode 100644 index 0000000000..79140655aa --- /dev/null +++ b/.github/workflows/build-ota-updates.yml @@ -0,0 +1,36 @@ +name: OTA translations + +on: + workflow_dispatch: + schedule: + # Every day at 10:11 UTC + - cron: '11 10 * * *' + +jobs: + build-ota-translations: + name: Build OTA translations + runs-on: ubuntu-latest + + steps: + - uses: actions/checkout@v4 + + - name: Install GNU gettext + run: sudo apt-get install gettext + + - name: Install Crowdin CLI + run: npm i -g @crowdin/cli + + - name: Download latest translations from Crowdin + run: | + echo 'api_token: "${{secrets.CROWDIN_PERSONAL_TOKEN}}"' >>crowdin.yaml + crowdin download + rm crowdin.yaml + + - name: Build OTA updates + run: scripts/build-ota-translations.sh + + - name: Upload OTA updates + run: | + VERSION=$(sed -n -e 's/.*POEDIT_VERSION.* "\([0-9]*\)\.\([0-9]*\).*".*/\1.\2/p' src/version.h) + echo "OTA version: $VERSION" + curl --fail-with-body -F 'data=@ota-update.tar' -H "X-Api-Key: ${{secrets.OTA_API_KEY}}" "${{secrets.OTA_UPLOAD_ENDPOINT}}?version=${VERSION}" From 41f3a89063dc957a998c158471dff23759eb6d1b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Va=CC=81clav=20Slavi=CC=81k?= Date: Wed, 1 Nov 2023 19:09:22 +0100 Subject: [PATCH 3/4] Normalize OTA translation requests Normalize language update requests to minimize cache misses and avoid re-downloads on minor version updates: - only use major.minor version number for version - normalize language code into xx[_YY] locale form --- src/edapp.cpp | 25 +++++++++++++++++++++---- src/edapp.h | 5 +++-- 2 files changed, 24 insertions(+), 6 deletions(-) diff --git a/src/edapp.cpp b/src/edapp.cpp index 15821aaef7..08bdc4a65b 100644 --- a/src/edapp.cpp +++ b/src/edapp.cpp @@ -293,6 +293,12 @@ wxString PoeditApp::GetAppVersion() const return wxString::FromAscii(POEDIT_VERSION); } +wxString PoeditApp::GetMajorAppVersion() const +{ + auto v = wxSplit(GetAppVersion(), '.'); + return wxString::Format("%s.%s", v[0], v[1]); +} + wxString PoeditApp::GetAppBuildNumber() const { #if defined(__WXOSX__) @@ -631,18 +637,29 @@ void PoeditApp::SetupLanguage() #endif #ifdef SUPPORTS_OTA_UPDATES - SetupOTALanguageUpdate(trans, str::to_utf8(bestTrans)); + SetupOTALanguageUpdate(trans, bestTrans); #endif } #ifdef SUPPORTS_OTA_UPDATES -void PoeditApp::SetupOTALanguageUpdate(wxTranslations *trans, const std::string& lang) +void PoeditApp::SetupOTALanguageUpdate(wxTranslations *trans, const wxString& lang) { if (lang == "en") return; + // normalize language code for requests + wxString langMO(lang); + if (langMO == "zh-Hans") + langMO = "zh_CN"; + else if (langMO == "zh-Hant") + langMO = "zh_TW"; + else + langMO.Replace("-", "_"); + + auto version = str::to_utf8(GetMajorAppVersion()); + // use downloaded OTA translations: - auto dir = GetCacheDir("Translations") + "/" + POEDIT_VERSION; + auto dir = GetCacheDir("Translations") + "/" + version; wxFileTranslationsLoader::AddCatalogLookupPathPrefix(dir); trans->AddCatalog("poedit-ota"); @@ -663,7 +680,7 @@ void PoeditApp::SetupOTALanguageUpdate(wxTranslations *trans, const std::string& if (!etag.empty()) hdrs.emplace_back("If-None-Match", etag); - http_client::download_from_anywhere("https://ota.poedit.net/i18n/" POEDIT_VERSION "/" + lang + "/poedit-ota.mo.gz", hdrs) + http_client::download_from_anywhere("https://ota.poedit.net/i18n/" + version + "/" + str::to_utf8(langMO) + "/poedit-ota.mo.gz", hdrs) .then_on_main([=](downloaded_file f) { TempOutputFileFor temp(mofile); diff --git a/src/edapp.h b/src/edapp.h index 87f35ebd8d..1fc253f95a 100644 --- a/src/edapp.h +++ b/src/edapp.h @@ -62,7 +62,8 @@ class PoeditApp : public wxApp, public MenusManager static wxString GetCacheDir(const wxString& category); /// Returns Poedit version string. - wxString GetAppVersion() const; + wxString GetAppVersion() const; // e.g. "3.4.2" + wxString GetMajorAppVersion() const; // e.g. "3.4" wxString GetAppBuildNumber() const; bool CheckForBetaUpdates() const; @@ -108,7 +109,7 @@ class PoeditApp : public wxApp, public MenusManager void SetupLanguage(); #ifdef SUPPORTS_OTA_UPDATES - void SetupOTALanguageUpdate(wxTranslations *trans, const std::string& lang); + void SetupOTALanguageUpdate(wxTranslations *trans, const wxString& lang); #endif // App-global menu commands: From 449fe8e02cd630e0c714aa2811790c5cae87d5be Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Va=CC=81clav=20Slavi=CC=81k?= Date: Thu, 2 Nov 2023 18:31:45 +0100 Subject: [PATCH 4/4] Support OTA updates in snap builds for Linux --- snap/snapcraft.yaml | 2 +- src/edapp.cpp | 2 +- src/edapp.h | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/snap/snapcraft.yaml b/snap/snapcraft.yaml index eecbd54598..93496bd26e 100644 --- a/snap/snapcraft.yaml +++ b/snap/snapcraft.yaml @@ -105,7 +105,7 @@ parts: ./bootstrap ./configure \ --with-wx-prefix="$SNAPCRAFT_STAGE" \ - CPPFLAGS="-I${SNAPCRAFT_STAGE}/include -I${SNAPCRAFT_PART_INSTALL}/../build/deps/json/src" \ + CPPFLAGS="-DSNAPCRAFT -I${SNAPCRAFT_STAGE}/include -I${SNAPCRAFT_PART_INSTALL}/../build/deps/json/src" \ LDFLAGS="-Wl,--copy-dt-needed-entries -L${SNAPCRAFT_STAGE}/lib" \ PKG_CONFIG_PATH="${SNAPCRAFT_STAGE}"/lib/pkgconfig make -j1 diff --git a/src/edapp.cpp b/src/edapp.cpp index 08bdc4a65b..5627d70b9a 100644 --- a/src/edapp.cpp +++ b/src/edapp.cpp @@ -644,7 +644,7 @@ void PoeditApp::SetupLanguage() #ifdef SUPPORTS_OTA_UPDATES void PoeditApp::SetupOTALanguageUpdate(wxTranslations *trans, const wxString& lang) { - if (lang == "en") + if (lang == "en" || lang == "en_US") return; // normalize language code for requests diff --git a/src/edapp.h b/src/edapp.h index 1fc253f95a..0097721771 100644 --- a/src/edapp.h +++ b/src/edapp.h @@ -39,7 +39,7 @@ class WXDLLIMPEXP_FWD_BASE wxConfigBase; class WXDLLIMPEXP_FWD_BASE wxSingleInstanceChecker; -#if defined(HAVE_HTTP_CLIENT) && (defined(__WXMSW__) || defined(__WXOSX__)) +#if defined(HAVE_HTTP_CLIENT) && (defined(__WXMSW__) || defined(__WXOSX__) || defined(SNAPCRAFT)) #define SUPPORTS_OTA_UPDATES #endif