Script 'mail_helper' called by obssrc
Hello community,

here is the log from the commit of package python-translation-finder for 
openSUSE:Factory checked in at 2024-01-03 12:24:19
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/python-translation-finder (Old)
 and      /work/SRC/openSUSE:Factory/.python-translation-finder.new.28375 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Package is "python-translation-finder"

Wed Jan  3 12:24:19 2024 rev:14 rq:1135631 version:2.16

Changes:
--------
--- 
/work/SRC/openSUSE:Factory/python-translation-finder/python-translation-finder.changes
      2023-03-21 17:44:57.226812852 +0100
+++ 
/work/SRC/openSUSE:Factory/.python-translation-finder.new.28375/python-translation-finder.changes
   2024-01-03 12:24:26.230269700 +0100
@@ -1,0 +2,8 @@
+Fri Dec 29 10:10:49 UTC 2023 - Dirk Müller <dmuel...@suse.com>
+
+- update to 2.16:
+  * Fixed detection UTF-16 Strings files.
+  * Fixed detection of files with some special chars.
+  * Added support for Mobile Kotlin resources.
+
+-------------------------------------------------------------------

Old:
----
  translation-finder-2.15.tar.gz

New:
----
  translation-finder-2.16.tar.gz

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Other differences:
------------------
++++++ python-translation-finder.spec ++++++
--- /var/tmp/diff_new_pack.N1661T/_old  2024-01-03 12:24:27.694323193 +0100
+++ /var/tmp/diff_new_pack.N1661T/_new  2024-01-03 12:24:27.694323193 +0100
@@ -21,7 +21,7 @@
 %define modname translation-finder
 %define skip_python2 1
 Name:           python-translation-finder
-Version:        2.15
+Version:        2.16
 Release:        0
 Summary:        Translation Files Finder
 License:        GPL-3.0-or-later

++++++ translation-finder-2.15.tar.gz -> translation-finder-2.16.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/.deepsource.toml 
new/translation-finder-2.16/.deepsource.toml
--- old/translation-finder-2.15/.deepsource.toml        2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.deepsource.toml        2023-12-20 
13:21:31.000000000 +0100
@@ -2,14 +2,17 @@
 #
 # SPDX-License-Identifier: GPL-3.0-or-later
 
-version = 1
 test_patterns = [
   "**/test_*.py"
 ]
+version = 1
 
 [[analyzers]]
-name = "python"
 enabled = true
+name = "python"
+
+[[analyzers]]
+name = "test-coverage"
 
 [analyzers.meta]
 runtime_version = "3.x.x"
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/.github/ISSUE_TEMPLATE/bug_report.yml 
new/translation-finder-2.16/.github/ISSUE_TEMPLATE/bug_report.yml
--- old/translation-finder-2.15/.github/ISSUE_TEMPLATE/bug_report.yml   
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/ISSUE_TEMPLATE/bug_report.yml   
2023-12-20 13:21:31.000000000 +0100
@@ -10,12 +10,18 @@
 - type: markdown
   attributes:
     value: |
-      Thank you for reporting an issue on Weblate! This form will guide you to 
create a useful issue report.
+      Thank you for reporting an issue.
+      This form guides you in creating a useful issue report.
+
+      Want your answer quickly and guaranteed? Visit 
https://weblate.org/support/ to reach our dedicated support team. As a 
subscriber, you will always have priority and help Weblate growing.
 - type: textarea
   id: what-happened
   attributes:
     label: Describe the issue
-    description: A clear and concise description of the problem you are facing.
+    description: >
+      A clear and concise description of the problem you are facing.
+
+      Please include important information, like the file format you are using 
and installed add-ons.
     placeholder: Tell us what you see!
   validations:
     required: true
@@ -23,26 +29,30 @@
   id: tried
   attributes:
     label: I already tried
-    description: If you didn’t try already, try to search the documentation 
and existing issues what you wrote above.
+    description: If you didn’t try already, try searching the documentation 
and existing issues.
     options:
     - label: I've read and searched [the 
documentation](https://docs.weblate.org/).
       required: true
-    - label: I've searched for similar issues in this repository.
+    - label: I've searched for similar filed issues in this repository.
       required: true
 - type: textarea
   id: reproducer
   attributes:
     label: Steps to reproduce the behavior
-    value: |
-      1. Go to '...'
-      2. Scroll down to '...'
-      3. Click on '...'
-      4. See error
+    description: What did you do before the problem appeared?
+    placeholder: |
+      1. Go to '…'
+      2. Scroll down to '…'
+      3. Click on '…'
+      4. The error occurs
+  validations:
+    required: true
 - type: textarea
   id: expected
   attributes:
     label: Expected behavior
     description: A clear and concise description of what you expected to 
happen.
+    placeholder: Tell us what you want to see!
 - type: textarea
   id: screenshots
   attributes:
@@ -53,14 +63,14 @@
   attributes:
     label: Exception traceback
     description: >
-      In case you observed server error or crash, please see
+      In case you observed a server error or crash, please read
       [the debugging 
documentation](https://docs.weblate.org/en/latest/contributing/debugging.html)
-      for information how to obtain that.
+      for information on obtaining the relevant logs.
 
-      This will be rendered as Python traceback automatically.
+      This field will be rendered as a Python traceback automatically.
     render: pytb
 - type: textarea
   id: additional
   attributes:
     label: Additional context
-    description: Add any other context about the problem here.
+    description: Add any other contextual info about the problem here.
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/.github/ISSUE_TEMPLATE/config.yml 
new/translation-finder-2.16/.github/ISSUE_TEMPLATE/config.yml
--- old/translation-finder-2.15/.github/ISSUE_TEMPLATE/config.yml       
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/ISSUE_TEMPLATE/config.yml       
2023-12-20 13:21:31.000000000 +0100
@@ -5,12 +5,12 @@
 # This file is maintained in https://github.com/WeblateOrg/meta/
 # and generated using update-issue-config there.
 contact_links:
-- name: Read our clear, thorough and localized Docs
+- name: Read our clear, thorough and localized docs
   url: https://docs.weblate.org/
   about: Save your time! There is an instant solution for many issues in the 
docs appreciated by numerous users. And it might be in your preferred language.
-- name: Get Professional support
+- name: Get professional support
   url: https://weblate.org/support/
   about: As a subscriber, you will always receive fast and helpful replies 
from our dedicated support team. More responsible and faster for your business, 
also makes Weblate stronger.
-- name: Ask a Question
+- name: Ask the community
   url: https://github.com/WeblateOrg/weblate/discussions
   about: Want to discuss something with a community? Do it in discussions!
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/.github/ISSUE_TEMPLATE/feature_request.yml 
new/translation-finder-2.16/.github/ISSUE_TEMPLATE/feature_request.yml
--- old/translation-finder-2.15/.github/ISSUE_TEMPLATE/feature_request.yml      
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/ISSUE_TEMPLATE/feature_request.yml      
2023-12-20 13:21:31.000000000 +0100
@@ -10,7 +10,10 @@
 - type: markdown
   attributes:
     value: |
-      Thank you for reporting an issue on Weblate! This form will guide you to 
create a useful issue report.
+      Thank you for requesting a change.
+      This form guides you in creating a useful feature request.
+
+      Want your answer quickly and guaranteed? Visit 
https://weblate.org/support/ to reach our dedicated support team. As a 
subscriber, you will always have priority and help Weblate growing.
 - type: textarea
   id: describe
   attributes:
@@ -18,21 +21,23 @@
     description: >
       Is your feature request related to a problem? If so, please provide
       a clear and concise description of what the problem is.
-      Ex. I'm always frustrated when [...]
+    placeholder: I'm always frustrated when…
   validations:
     required: true
 - type: textarea
-  id: solition
+  id: solution
   attributes:
-    label: Describe the solution you'd like
+    label: Describe the solution you would like
     description: A clear and concise description of what the new feature 
should do.
+    placeholder: I'd like to get…
   validations:
     required: true
 - type: textarea
   id: alternatives
   attributes:
-    label: Describe alternatives you've considered
-    description: A clear and concise description of any alternative solutions 
or features you've considered.
+    label: Describe alternatives you have considered
+    description: A clear and concise description of any alternative solutions 
or features you have considered.
+    placeholder: The issue can also be addressed by…
 - type: textarea
   id: screenshots
   attributes:
@@ -42,4 +47,4 @@
   id: additional
   attributes:
     label: Additional context
-    description: Add any other context about the problem here.
+    description: Add any other contextual info about the problem here.
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/.github/ISSUE_TEMPLATE/support_question.yml 
new/translation-finder-2.16/.github/ISSUE_TEMPLATE/support_question.yml
--- old/translation-finder-2.15/.github/ISSUE_TEMPLATE/support_question.yml     
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/ISSUE_TEMPLATE/support_question.yml     
1970-01-01 01:00:00.000000000 +0100
@@ -1,70 +0,0 @@
-# Copyright © Michal Čihař <mic...@weblate.org>
-#
-# SPDX-License-Identifier: CC0-1.0
-
-# This file is maintained in https://github.com/WeblateOrg/meta/
-# and generated from .github/ISSUE_TEMPLATE/snippets there.
-name: Support question
-description: Help with configuration or deployment
-labels:
-- question
-body:
-- type: markdown
-  attributes:
-    value: |
-      Thank you for reporting an issue on Weblate! This form will guide you to 
create a useful issue report.
-
-      Want your answer quickly and guaranteed? Visit 
https://weblate.org/support/ to reach our dedicated support team. As a 
subscriber, you will always have priority and help Weblate growing.
-- type: textarea
-  id: what-happened
-  attributes:
-    label: Describe the issue
-    description: A clear and concise description of the problem you are facing.
-    placeholder: Tell us what you see!
-  validations:
-    required: true
-- type: checkboxes
-  id: tried
-  attributes:
-    label: I already tried
-    description: If you didn’t try already, try to search the documentation 
and existing issues what you wrote above.
-    options:
-    - label: I've read and searched [the 
documentation](https://docs.weblate.org/).
-      required: true
-    - label: I've searched for similar issues in this repository.
-      required: true
-- type: textarea
-  id: reproducer
-  attributes:
-    label: Steps to reproduce the behavior
-    value: |
-      1. Go to '...'
-      2. Scroll down to '...'
-      3. Click on '...'
-      4. See error
-- type: textarea
-  id: expected
-  attributes:
-    label: Expected behavior
-    description: A clear and concise description of what you expected to 
happen.
-- type: textarea
-  id: screenshots
-  attributes:
-    label: Screenshots
-    description: If applicable, add screenshots to better explain your problem.
-- type: textarea
-  id: traceback
-  attributes:
-    label: Exception traceback
-    description: >
-      In case you observed server error or crash, please see
-      [the debugging 
documentation](https://docs.weblate.org/en/latest/contributing/debugging.html)
-      for information how to obtain that.
-
-      This will be rendered as Python traceback automatically.
-    render: pytb
-- type: textarea
-  id: additional
-  attributes:
-    label: Additional context
-    description: Add any other context about the problem here.
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/.github/labels.yml 
new/translation-finder-2.16/.github/labels.yml
--- old/translation-finder-2.15/.github/labels.yml      2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/labels.yml      2023-12-20 
13:21:31.000000000 +0100
@@ -32,7 +32,7 @@
 # Automated dependency updates
 - color: e3f49c
   name: dependencies
-  description: Pull requests that update a dependency file.
+  description: Third-party library dependencies.
 # Hacktoberfest
 - color: 7057ff
   name: hacktoberfest
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/.github/matchers/flake8.json 
new/translation-finder-2.16/.github/matchers/flake8.json
--- old/translation-finder-2.15/.github/matchers/flake8.json    2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/matchers/flake8.json    1970-01-01 
01:00:00.000000000 +0100
@@ -1,17 +0,0 @@
-{
-  "problemMatcher": [
-    {
-      "owner": "flake8",
-      "pattern": [
-        {
-          "code": 4,
-          "column": 3,
-          "file": 1,
-          "line": 2,
-          "message": 5,
-          "regexp": "^([^:]*):(\\d+):(\\d+): (\\w+\\d\\d\\d) (.*)$"
-        }
-      ]
-    }
-  ]
-}
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/.github/matchers/flake8.json.license 
new/translation-finder-2.16/.github/matchers/flake8.json.license
--- old/translation-finder-2.15/.github/matchers/flake8.json.license    
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/matchers/flake8.json.license    
1970-01-01 01:00:00.000000000 +0100
@@ -1,5 +0,0 @@
-Copyright © Michal Čihař <mic...@weblate.org>
-
-SPDX-License-Identifier: CC0-1.0
-
-This file is maintained in https://github.com/WeblateOrg/meta/
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/.github/renovate.json 
new/translation-finder-2.16/.github/renovate.json
--- old/translation-finder-2.15/.github/renovate.json   2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/renovate.json   2023-12-20 
13:21:31.000000000 +0100
@@ -28,10 +28,35 @@
       "schedule": "on the last day of the month"
     },
     {
+      "matchDatasources": [
+        "helm"
+      ],
+      "automerge": false,
+      "schedule": "on the last day of the month"
+    },
+    {
       "matchPaths": [
         "**/package.json"
       ],
       "automerge": false
+    },
+    {
+      "matchPackageNames": [
+        "shellcheck-py/shellcheck-py"
+      ],
+      "versioning": "loose"
+    },
+    {
+      "matchPackageNames": [
+        "python"
+      ],
+      "matchDatasources": [
+        "docker"
+      ],
+      "separateMinorPatch": true,
+      "minor": {
+        "dependencyDashboardApproval": true
+      }
     }
   ],
   "regexManagers": [
@@ -54,6 +79,44 @@
       ],
       "datasourceTemplate": "npm",
       "versioningTemplate": "npm"
+    },
+    {
+      "fileMatch": [
+        "^Dockerfile$"
+      ],
+      "matchStrings": [
+        "ENV WEBLATE_VERSION (?<currentValue>.*?)\\n"
+      ],
+      "depNameTemplate": "Weblate",
+      "datasourceTemplate": "pypi",
+      "versioningTemplate": "pep440"
+    },
+    {
+      "fileMatch": [
+        "(^|/)Chart\\.yaml$"
+      ],
+      "matchStrings": [
+        "renovate: datasource=(?<datasource>.*?) depName=(?<depName>.*?)( 
versioning=(?<versioning>.*?))?\\s+appVersion: (?<currentValue>.*)\\s"
+      ]
+    },
+    {
+      "fileMatch": [
+        "^\\.github/workflows/[^/]+\\.ya?ml$"
+      ],
+      "matchStrings": [
+        "renovate: datasource=(?<datasource>.*?) depName=(?<depName>.*?)( 
versioning=(?<versioning>.*?))?\\s+version: (?<currentValue>.*)\\s"
+      ]
+    },
+    {
+      "fileMatch": [
+        "weblate_web/data.py"
+      ],
+      "matchStrings": [
+        "VERSION = \"(?<currentValue>.*?)\""
+      ],
+      "depNameTemplate": "Weblate",
+      "datasourceTemplate": "pypi",
+      "versioningTemplate": "pep440"
     }
   ]
 }
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/.github/workflows/closing.yml 
new/translation-finder-2.16/.github/workflows/closing.yml
--- old/translation-finder-2.15/.github/workflows/closing.yml   2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/workflows/closing.yml   2023-12-20 
13:21:31.000000000 +0100
@@ -20,7 +20,7 @@
     runs-on: ubuntu-22.04
     steps:
     - name: Add closed question comment
-      uses: peter-evans/create-or-update-comment@v2
+      uses: peter-evans/create-or-update-comment@v3
       if: |
         github.actor != 'renovate[bot]' &&
         github.event.issue.state_reason == 'completed' &&
@@ -34,7 +34,7 @@
           * In case you see a similar problem, please open a separate issue.
           * If you are happy with the outcome, don’t hesitate to support 
Weblate by making a [donation](https://weblate.org/donate/).
     - name: Add closed issue comment
-      uses: peter-evans/create-or-update-comment@v2
+      uses: peter-evans/create-or-update-comment@v3
       if: |
         github.actor != 'renovate[bot]' &&
         github.event.issue.state_reason == 'completed' &&
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/.github/workflows/codeql-analysis.yml 
new/translation-finder-2.16/.github/workflows/codeql-analysis.yml
--- old/translation-finder-2.15/.github/workflows/codeql-analysis.yml   
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/workflows/codeql-analysis.yml   
2023-12-20 13:21:31.000000000 +0100
@@ -18,22 +18,22 @@
 jobs:
   analyze:
     name: Analyze
-    runs-on: ubuntu-20.04
+    runs-on: ubuntu-22.04
     strategy:
       fail-fast: false
       matrix:
         language: [python]
     steps:
     - name: Checkout repository
-      uses: actions/checkout@v3
+      uses: actions/checkout@v4
 
     - name: Initialize CodeQL
-      uses: github/codeql-action/init@v2
+      uses: github/codeql-action/init@v3
       with:
         languages: ${{ matrix.language }}
 
     - name: Autobuild
-      uses: github/codeql-action/autobuild@v2
+      uses: github/codeql-action/autobuild@v3
 
     - name: Perform CodeQL Analysis
-      uses: github/codeql-action/analyze@v2
+      uses: github/codeql-action/analyze@v3
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/.github/workflows/flake8.yml 
new/translation-finder-2.16/.github/workflows/flake8.yml
--- old/translation-finder-2.15/.github/workflows/flake8.yml    2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/workflows/flake8.yml    1970-01-01 
01:00:00.000000000 +0100
@@ -1,43 +0,0 @@
-# Copyright © Michal Čihař <mic...@weblate.org>
-#
-# SPDX-License-Identifier: CC0-1.0
-
-# This file is maintained in https://github.com/WeblateOrg/meta/
-name: Flake8
-
-on:
-  push:
-    branches-ignore:
-    - deepsource-fix-**
-    - renovate/**
-    - weblate
-  pull_request:
-
-permissions:
-  contents: read
-
-jobs:
-  flake8:
-    runs-on: ubuntu-22.04
-
-    steps:
-    - uses: actions/checkout@v3
-    - uses: actions/cache@v3
-      with:
-        path: |
-          ~/.cache/pip
-          ~/.cache/pre-commit
-        key: ${{ runner.os }}-pre-commit-${{ hashFiles('**/requirements*.txt') 
}}-${{ hashFiles('.pre-commit-config.yaml') }}
-    - name: Setup Python
-      uses: actions/setup-python@v4
-      with:
-        python-version: '3.11'
-    - name: Install dependencies
-      run: |
-        python -m pip install --upgrade pip wheel
-        pip install -r requirements-lint.txt
-    - name: Run flake8
-      run: |
-        echo "::add-matcher::.github/matchers/flake8.json"
-        pre-commit run flake8 --all
-        echo "::remove-matcher owner=flake8::"
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/.github/workflows/label-sync.yml 
new/translation-finder-2.16/.github/workflows/label-sync.yml
--- old/translation-finder-2.15/.github/workflows/label-sync.yml        
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/workflows/label-sync.yml        
2023-12-20 13:21:31.000000000 +0100
@@ -14,17 +14,14 @@
     - .github/workflows/label-sync.yml
 
 permissions:
-  contents: read
+  issues: write
 
 jobs:
   build:
     name: Sync labels
     runs-on: ubuntu-22.04
     steps:
-    - uses: actions/checkout@v3
-    - uses: micnncim/action-label-syncer@v1.3.0
-      env:
-        GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
-        GITHUB_REPOSITORY: ${{ github.repository }}
+    - uses: actions/checkout@v4
+    - uses: srealmoreno/label-sync-action@v1
       with:
-        manifest: .github/labels.yml
+        clean-labels: true
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/.github/workflows/labels.yml 
new/translation-finder-2.16/.github/workflows/labels.yml
--- old/translation-finder-2.15/.github/workflows/labels.yml    2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/workflows/labels.yml    2023-12-20 
13:21:31.000000000 +0100
@@ -20,7 +20,7 @@
     runs-on: ubuntu-22.04
     steps:
     - name: Add backlog comment
-      uses: peter-evans/create-or-update-comment@v2
+      uses: peter-evans/create-or-update-comment@v3
       if: ${{ github.event.label.name == 'backlog' }}
       with:
         token: ${{ secrets.GITHUB_TOKEN }}
@@ -33,7 +33,7 @@
           In case you need this feature soon, please consider helping
           or push it by [funding the 
development](https://weblate.org/support/).
     - name: Add undecided comment
-      uses: peter-evans/create-or-update-comment@v2
+      uses: peter-evans/create-or-update-comment@v3
       if: ${{ github.event.label.name == 'undecided' }}
       with:
         token: ${{ secrets.GITHUB_TOKEN }}
@@ -46,21 +46,24 @@
 
           Please try to clarify the use case or consider proposing something 
more generic to make it useful to more users.
     - name: Add question comment
-      uses: peter-evans/create-or-update-comment@v2
+      uses: peter-evans/create-or-update-comment@v3
       if: ${{ github.event.label.name == 'question' }}
       with:
         token: ${{ secrets.GITHUB_TOKEN }}
         issue-number: ${{ github.event.issue.number }}
         body: >
-          This issue looks more like a support question than an
-          issue. We strive to answer these reasonably fast, but
+          This issue has been marked as a question by a Weblate team member.
+          Why? Because it belongs more to the professional [Weblate 
Care](https://care.weblate.org/)
+          or community 
[Discussions](https://github.com/WeblateOrg/weblate/discussions) than here.
+          We strive to answer these reasonably fast here, too, but
           [purchasing the support subscription](https://weblate.org/support/)
-          is not only more responsible and faster for your business but also 
makes Weblate stronger.
+          is more responsible and faster for your business.
+          And it makes Weblate stronger as well. Thanks!
 
 
           In case your question is already answered, [making a 
donation](https://weblate.org/donate/) is the right way to say thank you!
     - name: Add translate-toolkit comment
-      uses: peter-evans/create-or-update-comment@v2
+      uses: peter-evans/create-or-update-comment@v3
       if: ${{ github.event.label.name == 'translate-toolkit' }}
       with:
         token: ${{ secrets.GITHUB_TOKEN }}
@@ -69,7 +72,7 @@
           The issue you've reported needs to be addressed in the 
[translate-toolkit](https://github.com/translate/translate/).
           Please file the issue there, and include links to any relevant 
specifications about the formats (if applicable).
     - name: Add good first issue comment
-      uses: peter-evans/create-or-update-comment@v2
+      uses: peter-evans/create-or-update-comment@v3
       if: ${{ github.event.label.name == 'good first issue' }}
       with:
         token: ${{ secrets.GITHUB_TOKEN }}
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/.github/workflows/pre-commit.yml 
new/translation-finder-2.16/.github/workflows/pre-commit.yml
--- old/translation-finder-2.15/.github/workflows/pre-commit.yml        
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/workflows/pre-commit.yml        
2023-12-20 13:21:31.000000000 +0100
@@ -21,20 +21,25 @@
     runs-on: ubuntu-22.04
 
     steps:
-    - uses: actions/checkout@v3
+    - uses: actions/checkout@v4
     - uses: actions/cache@v3
       with:
         path: |
           ~/.cache/pip
           ~/.cache/pre-commit
-        key: ${{ runner.os }}-pre-commit-${{ hashFiles('**/requirements*.txt') 
}}-${{ hashFiles('.pre-commit-config.yaml') }}
+        key: ${{ runner.os }}-pre-commit-${{ hashFiles('**/requirements*.txt') 
}}-${{ hashFiles('.pre-commit-config.yaml') }}-${{ hashFiles('pyproject.toml') 
}}
     - name: Setup Python
-      uses: actions/setup-python@v4
+      uses: actions/setup-python@v5
       with:
         python-version: '3.11'
+    - name: Update pip
+      run: python -m pip install --upgrade pip wheel
     - name: Install dependencies
       run: |
-        python -m pip install --upgrade pip wheel
-        pip install -r requirements-lint.txt
+        if [ -f requirements-lint.txt ] ; then
+          pip install -r requirements-lint.txt
+        else
+          pip install -e .[lint]
+        fi
     - name: pre-commit
       run: pre-commit run --all
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/.github/workflows/pull_requests.yaml 
new/translation-finder-2.16/.github/workflows/pull_requests.yaml
--- old/translation-finder-2.15/.github/workflows/pull_requests.yaml    
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/workflows/pull_requests.yaml    
2023-12-20 13:21:31.000000000 +0100
@@ -22,7 +22,7 @@
     name: Weblate automerge
     if: github.actor == 'weblate'
     steps:
-    - uses: peter-evans/enable-pull-request-automerge@v2
+    - uses: peter-evans/enable-pull-request-automerge@v3
       with:
         pull-request-number: ${{ github.event.pull_request.number }}
         merge-method: rebase
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/.github/workflows/setup.yml 
new/translation-finder-2.16/.github/workflows/setup.yml
--- old/translation-finder-2.15/.github/workflows/setup.yml     2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/workflows/setup.yml     2023-12-20 
13:21:31.000000000 +0100
@@ -8,18 +8,18 @@
 
 jobs:
   setup:
-    runs-on: ubuntu-20.04
+    runs-on: ubuntu-22.04
 
     steps:
-    - uses: actions/checkout@v3
+    - uses: actions/checkout@v4
     - uses: actions/cache@v3
       with:
         path: ~/.cache/pip
         key: ${{ runner.os }}-pip-setup-${{ hashFiles('**/requirements*.txt') 
}}
     - name: Setup Python
-      uses: actions/setup-python@v4
+      uses: actions/setup-python@v5
       with:
-        python-version: '3.10'
+        python-version: '3.11'
     - name: Install dependencies
       run: |
         python -m pip install --upgrade pip wheel
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/.github/workflows/stale.yml 
new/translation-finder-2.16/.github/workflows/stale.yml
--- old/translation-finder-2.15/.github/workflows/stale.yml     2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/workflows/stale.yml     2023-12-20 
13:21:31.000000000 +0100
@@ -26,13 +26,14 @@
       pull-requests: write
 
     steps:
-    - uses: actions/stale@v7
+    - uses: actions/stale@v9
       with:
         days-before-pr-stale: 30
         days-before-pr-close: 14
-        days-before-stale: 10
-        days-before-close: 4
-        exempt-issue-labels: bug,enhancement,documentation,security
+        days-before-stale: 14
+        days-before-close: 5
+        exempt-issue-labels: 
bug,enhancement,documentation,security,dependencies
+        exempt-pr-labels: backlog
         stale-issue-label: wontfix
         stale-pr-label: wontfix
         repo-token: ${{ secrets.GITHUB_TOKEN }}
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/.github/workflows/test.yml 
new/translation-finder-2.16/.github/workflows/test.yml
--- old/translation-finder-2.15/.github/workflows/test.yml      2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.github/workflows/test.yml      2023-12-20 
13:21:31.000000000 +0100
@@ -11,39 +11,42 @@
     runs-on: ${{ matrix.os }}
     strategy:
       matrix:
-        os: [ubuntu-20.04, windows-latest, macos-latest]
+        os:
+        - ubuntu-latest
+        - windows-latest
+        - macos-latest
         python-version:
-        - '3.7'
-        - '3.8'
         - '3.9'
         - '3.10'
+        - '3.11'
+        - '3.12'
         exclude:
         - os: windows-latest
-          python-version: 3.8
-        - os: windows-latest
-          python-version: 3.9
+          python-version: '3.10'
         - os: macos-latest
-          python-version: 3.8
+          python-version: '3.10'
+        - os: windows-latest
+          python-version: '3.11'
         - os: macos-latest
-          python-version: 3.9
+          python-version: '3.11'
     name: ${{ matrix.os }}, Python ${{ matrix.python-version }}
 
     steps:
-    - uses: actions/checkout@v3
+    - uses: actions/checkout@v4
     - name: Cache pip
       uses: actions/cache@v3
       with:
         path: ~/.cache/pip
         key: ${{ runner.os }}-pip-${{ matrix.python-version }}-${{ 
hashFiles('**/requirements*.txt') }}
     - name: Set up Python ${{ matrix.python-version }}
-      uses: actions/setup-python@v4
+      uses: actions/setup-python@v5
       with:
         python-version: ${{ matrix.python-version }}
     - name: Install pip dependencies
       run: |
         python -m pip install --upgrade pip wheel
         pip install --upgrade 
https://github.com/WeblateOrg/language-data/archive/main.zip
-        pip install -r requirements-dev.txt
+        pip install -r requirements-test.txt
     - name: Test
       run: |
         py.test --cov=translation_finder translation_finder README.rst
@@ -56,10 +59,10 @@
         flags: unittests
         name: Python ${{ matrix.python-version }}, ${{ matrix.os }}
     - name: DeepSource
-      if: matrix.os == 'ubuntu-20.04'
+      if: matrix.os == 'ubuntu-latest'
       continue-on-error: true
       env:
-        DEEPSOURCE_DSN: https://9685c29f2360413798cabd1422306...@deepsource.io
+        DEEPSOURCE_DSN: ${{secrets.DEEPSOURCE_DSN}}
       run: |
         curl https://deepsource.io/cli | sh
         ./bin/deepsource report --analyzer test-coverage --key python 
--value-file ./coverage.xml
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/.pre-commit-config.yaml 
new/translation-finder-2.16/.pre-commit-config.yaml
--- old/translation-finder-2.15/.pre-commit-config.yaml 2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/.pre-commit-config.yaml 2023-12-20 
13:21:31.000000000 +0100
@@ -5,41 +5,8 @@
 # See https://pre-commit.com for more information
 # See https://pre-commit.com/hooks.html for more hooks
 repos:
-- repo: https://github.com/PyCQA/isort
-  rev: 5.11.4
-  hooks:
-  - id: isort
-- repo: https://github.com/asottile/pyupgrade
-  rev: v3.3.1
-  hooks:
-  - id: pyupgrade
-    args: [--py37-plus]
-- repo: https://github.com/psf/black
-  rev: 22.12.0
-  hooks:
-  - id: black
-- repo: https://github.com/PyCQA/flake8
-  rev: 5.0.4
-  hooks:
-  - id: flake8
-    additional_dependencies:
-    - flake8-bugbear==22.12.6
-    - flake8-builtins==2.1.0
-    - flake8-comprehensions==3.10.1
-    - flake8-django==1.1.5
-    - flake8-docstrings==1.6.0
-    - flake8-eradicate==1.4.0
-    - flake8-executable==2.1.2
-    - flake8-logging-format==0.9.0
-    - flake8-mutable==1.2.0
-    - flake8-polyfill==1.0.2
-    - flake8-print==5.0.0
-    - flake8-return==1.2.0
-    - flake8-self==0.2.2
-    - flake8-assertive==2.1.0
-    - pep8-naming==0.13.3
 - repo: https://github.com/pre-commit/pre-commit-hooks
-  rev: v4.4.0
+  rev: v4.5.0
   hooks:
   - id: trailing-whitespace
   - id: end-of-file-fixer
@@ -48,17 +15,23 @@
   - id: requirements-txt-fixer
   - id: check-merge-conflict
   - id: check-json
+  - id: debug-statements
   - id: mixed-line-ending
     args: [--fix=lf]
-  - id: debug-statements
   - id: pretty-format-json
     args: [--no-sort-keys, --autofix, --no-ensure-ascii]
 - repo: https://github.com/adrienverge/yamllint
-  rev: v1.29.0
+  rev: v1.33.0
   hooks:
   - id: yamllint
+- repo: https://github.com/astral-sh/ruff-pre-commit
+  rev: v0.1.8
+  hooks:
+  - id: ruff
+    args: [--fix, --exit-non-zero-on-fix]
+  - id: ruff-format
 - repo: https://github.com/asottile/blacken-docs
-  rev: v1.12.1
+  rev: 1.16.0
   hooks:
   - id: blacken-docs
 - repo: meta
@@ -66,24 +39,28 @@
   - id: check-hooks-apply
   - id: check-useless-excludes
 - repo: https://github.com/macisamuele/language-formatters-pre-commit-hooks
-  rev: v2.5.0
+  rev: v2.11.0
   hooks:
   - id: pretty-format-yaml
     args: [--autofix, --indent, '2']
+  - id: pretty-format-toml
+    args: [--autofix]
 - repo: https://github.com/executablebooks/mdformat
-  rev: 0.7.16
+  rev: 0.7.17
   hooks:
   - id: mdformat
     additional_dependencies:
-    - mdformat-gfm
-    - mdformat-black
-    - mdformat-shfmt
+    - mdformat-gfm==0.3.5
+    - mdformat-black==0.1.1
+    - mdformat-shfmt==0.1.0
 - repo: https://github.com/igorshubovych/markdownlint-cli
-  rev: v0.33.0
+  rev: v0.38.0
   hooks:
   - id: markdownlint
 - repo: https://github.com/fsfe/reuse-tool
-  rev: v1.1.0
+  rev: v2.1.0
   hooks:
   - id: reuse
 exclude: 
^.*\.(properties)|translation_finder/test_data/app/src/res/main/values-it/strings.xml|translation_finder/test_data/app/src/res/main/values/strings.xml|translation_finder/test_data/json/bom-en.json|translation_finder/test_data/yaml/en/corrupt.yml$
+ci:
+  autoupdate_schedule: quarterly
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/CHANGES.rst 
new/translation-finder-2.16/CHANGES.rst
--- old/translation-finder-2.15/CHANGES.rst     2023-01-13 13:43:37.000000000 
+0100
+++ new/translation-finder-2.16/CHANGES.rst     2023-12-20 13:21:31.000000000 
+0100
@@ -1,6 +1,14 @@
 Changelog
 =========
 
+2.16
+----
+
+* Released on 20th December 2023.
+* Fixed detection UTF-16 Strings files.
+* Fixed detection of files with some special chars.
+* Added support for Mobile Kotlin resources.
+
 2.15
 ----
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/README.rst 
new/translation-finder-2.16/README.rst
--- old/translation-finder-2.15/README.rst      2023-01-13 13:43:37.000000000 
+0100
+++ new/translation-finder-2.16/README.rst      2023-12-20 13:21:31.000000000 
+0100
@@ -3,7 +3,7 @@
    :target: https://weblate.org/
    :height: 80px
 
-**Weblate is a copylefted libre software web-based continuous localization 
system,
+**Weblate is libre software web-based continuous localization system,
 used by over 2500 libre projects and companies in more than 165 countries.**
 
 A translation file finder for `Weblate`_, translation tool with tight version
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/SECURITY.md 
new/translation-finder-2.16/SECURITY.md
--- old/translation-finder-2.15/SECURITY.md     2023-01-13 13:43:37.000000000 
+0100
+++ new/translation-finder-2.16/SECURITY.md     2023-12-20 13:21:31.000000000 
+0100
@@ -6,13 +6,15 @@
 This file is maintained in https://github.com/WeblateOrg/meta/
 -->
 
-# Weblate Security
+# Weblate security
 
-We take security very seriously at Weblate. We welcome any peer review of our
-100% open source code to ensure nobody's Weblate is ever compromised or hacked.
+The Weblate team takes security and related transparency very seriously.
+We welcome any peer review of our 100% open-source code to ensure nobody's 
Weblate
+is ever compromised or hacked.
 
-You can find more information on reporting security issues in
-[our documentation][1] and on [our page at HackerOne][2].
+Information about practices for reporting and fixing security issues is 
described
+in [our documentation][1] and on [our page at HackerOne][2]. This ensures all
+vulnerabilities are solved securely, quickly, and transparently.
 
 [1]: https://docs.weblate.org/en/latest/contributing/issues.html#security
 [2]: https://hackerone.com/weblate
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/pyproject.toml 
new/translation-finder-2.16/pyproject.toml
--- old/translation-finder-2.15/pyproject.toml  2023-01-13 13:43:37.000000000 
+0100
+++ new/translation-finder-2.16/pyproject.toml  2023-12-20 13:21:31.000000000 
+0100
@@ -1,2 +1,54 @@
 [tool.black]
-target-version = ['py37']
+target-version = ['py39']
+
+[tool.isort]
+profile = "black"
+
+[tool.ruff]
+ignore = [
+  "D10",  # TODO: we are missing many docstrings
+  "D203",  # CONFIG: incompatible with D211
+  "D212",  # CONFIG: incompatible with D213
+  "D401",  # TODO: many strings need rephrasing
+  "RUF012",  # TODO: Mutable class attributes should be annotated with 
`typing.ClassVar`
+  "PLW2901"  # TODO: overwriting variables inside loop
+]
+output-format = "github"
+select = [
+  "E",
+  "F",
+  "B",
+  "T10",
+  "A",
+  "C4",
+  "C90",
+  "YTT",
+  "DJ",
+  "UP",
+  "D",
+  "PD",
+  "PGH",
+  "PL",
+  "TRY",
+  "RUF",
+  "ERA",
+  "ICN",
+  "ISC",
+  "EXE",
+  "INP",
+  "PIE",
+  "G",
+  "PYI",
+  "Q",
+  "SIM",
+  "TID",
+  "RSE",
+  "T20",
+  "RET",
+  "SLF",
+  "N"
+]
+target-version = "py39"
+
+[tool.ruff.mccabe]
+max-complexity = 16
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/requirements-lint.txt 
new/translation-finder-2.16/requirements-lint.txt
--- old/translation-finder-2.15/requirements-lint.txt   2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/requirements-lint.txt   2023-12-20 
13:21:31.000000000 +0100
@@ -1 +1 @@
-pre-commit==2.21.0
+pre-commit==3.6.0
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/setup.cfg 
new/translation-finder-2.16/setup.cfg
--- old/translation-finder-2.15/setup.cfg       2023-01-13 13:43:37.000000000 
+0100
+++ new/translation-finder-2.16/setup.cfg       2023-12-20 13:21:31.000000000 
+0100
@@ -1,6 +1,6 @@
 [metadata]
 name = translation-finder
-version = 2.15
+version = 2.16
 description = A translation file finder used in Weblate.
 long_description = file: README.rst
 long_description_content_type = text/x-rst
@@ -18,10 +18,6 @@
     Programming Language :: Python
     Programming Language :: Python :: 3
     Programming Language :: Python :: 3 :: Only
-    Programming Language :: Python :: 3.7
-    Programming Language :: Python :: 3.8
-    Programming Language :: Python :: 3.9
-    Programming Language :: Python :: 3.10
     Topic :: Software Development :: Internationalization
     Topic :: Software Development :: Localization
     Topic :: Utilities
@@ -36,7 +32,7 @@
 
 [options]
 packages = translation_finder,translation_finder.discovery
-python_requires = >=3.7
+python_requires = >=3.9
 package_dir = translation_finder=translation_finder
 include_package_data = 1
 
@@ -62,11 +58,3 @@
 extend-select = E,W1,W2,W3,W504,W505,W6
 exclude = 
migrations,settings.py,settings_test.py,.git,data,data-test,settings_test_nose.py,docs,.venv,build,node_modules,.eggs
 max-line-length = 88
-
-[isort]
-multi_line_output = 3
-include_trailing_comma = True
-force_grid_wrap = 0
-use_parentheses = True
-line_length = 88
-known_third_party = weblate_language_data,ruamel
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/translation_finder/discovery/base.py 
new/translation-finder-2.16/translation_finder/discovery/base.py
--- old/translation-finder-2.15/translation_finder/discovery/base.py    
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/translation_finder/discovery/base.py    
2023-12-20 13:21:31.000000000 +0100
@@ -7,13 +7,14 @@
 import fnmatch
 import re
 from itertools import chain
-from typing import Dict, Optional
+from typing import Optional
 
 from charset_normalizer import detect
 from weblate_language_data.country_codes import COUNTRIES
 from weblate_language_data.language_codes import LANGUAGES
 
-from ..data import LANGUAGES_BLACKLIST
+from translation_finder.data import LANGUAGES_BLACKLIST
+
 from .result import DiscoveryResult
 
 TOKEN_SPLIT = re.compile(r"([_.-])")
@@ -100,9 +101,11 @@
         return ""
 
     def get_wildcard(self, part: str):
-        """Generate language wilcard for a path part.
+        """
+        Generate language wilcard for a path part.
 
-        Retruns None if not possible."""
+        Retruns None if not possible.
+        """
         if self.is_language_code(part):
             return "*"
         if "." in part:
@@ -134,7 +137,7 @@
                     )
         return None
 
-    def fill_in_new_base(self, result: Dict[str, str]):
+    def fill_in_new_base(self, result: dict[str, str]):
         if not self.new_base_mask:
             return
         path = result["filemask"]
@@ -144,9 +147,7 @@
                 basename = basename.replace(match, replacement)
         new_name = self.new_base_mask.replace("*", basename).lower()
 
-        new_regex = "{}|{}".format(
-            re.escape(new_name), fnmatch.translate(self.new_base_mask)
-        )
+        new_regex = 
f"{re.escape(new_name)}|{fnmatch.translate(self.new_base_mask)}"
 
         best_result = None
 
@@ -183,7 +184,7 @@
                 yield mask.replace(match, replacement)
 
     def fill_in_template(
-        self, result: Dict[str, str], source_language: Optional[str] = None
+        self, result: dict[str, str], source_language: Optional[str] = None
     ):
         if "template" not in result:
             if source_language is None:
@@ -195,12 +196,12 @@
                     result["template"] = template
                     break
 
-    def fill_in_file_format(self, result: Dict[str, str]):
+    def fill_in_file_format(self, result: dict[str, str]):
         if "file_format" not in result:
             result["file_format"] = self.file_format
 
     @staticmethod
-    def adjust_format(result: Dict[str, str]):
+    def adjust_format(result: dict[str, str]):
         return
 
     def discover(self, eager: bool = False, hint: Optional[str] = None):
@@ -233,9 +234,11 @@
         )
 
     def get_masks(self, eager: bool = False, hint: Optional[str] = None):
-        """Return all file masks found in the directory.
+        """
+        Return all file masks found in the directory.
 
-        It is expected to contain duplicates."""
+        It is expected to contain duplicates.
+        """
         if hint:
             for mask in self.masks_list:
                 if fnmatch.fnmatch(hint, mask):
@@ -270,7 +273,7 @@
 
     uses_template = True
 
-    def fill_in_new_base(self, result: Dict[str, str]):
+    def fill_in_new_base(self, result: dict[str, str]):
         if "new_base" not in result and "template" in result:
             result["new_base"] = result["template"]
 
@@ -280,7 +283,7 @@
 
     encoding_map = {}
 
-    def adjust_format(self, result: Dict[str, str]):
+    def adjust_format(self, result: dict[str, str]):
         encoding = None
         matches = [self.finder.mask_matches(result["filemask"])]
         if "template" in result:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/translation_finder/discovery/files.py 
new/translation-finder-2.16/translation_finder/discovery/files.py
--- old/translation-finder-2.15/translation_finder/discovery/files.py   
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/translation_finder/discovery/files.py   
2023-12-20 13:21:31.000000000 +0100
@@ -6,12 +6,13 @@
 
 import json
 import re
-from typing import Dict, Optional
+from typing import Optional
 
 from ruamel.yaml import YAML
 from ruamel.yaml.error import YAMLError, YAMLFutureWarning
 
-from ..api import register_discovery
+from translation_finder.api import register_discovery
+
 from .base import BaseDiscovery, EncodingDiscovery, MonoTemplateDiscovery
 
 LARAVEL_RE = re.compile(r"=>.*\|")
@@ -69,13 +70,10 @@
     file_format = "xliff"
     mask = ("*.xliff", "*.xlf", "*.sdlxliff", "*.mxliff", "*.poxliff")
 
-    def adjust_format(self, result: Dict[str, str]):
-        if "template" in result:
-            base = result["template"]
-        else:
-            base = result["filemask"]
+    def adjust_format(self, result: dict[str, str]):
+        base = result["template"] if "template" in result else 
result["filemask"]
 
-        path = list(self.finder.mask_matches(base))[0]
+        path = next(iter(self.finder.mask_matches(base)))
 
         if not hasattr(path, "open"):
             return
@@ -119,9 +117,11 @@
     file_format = "aresource"
 
     def get_masks(self, eager: bool = False, hint: Optional[str] = None):
-        """Return all file masks found in the directory.
+        """
+        Return all file masks found in the directory.
 
-        It is expected to contain duplicates."""
+        It is expected to contain duplicates.
+        """
         for path in self.finder.filter_files(r"strings.*\.xml", ".*/values"):
             mask = list(path.parts)
             mask[-2] = "values-*"
@@ -130,18 +130,41 @@
 
 
 @register_discovery
+class MOKODiscovery(BaseDiscovery):
+    """Mobile Kotlin resources discovery."""
+
+    file_format = "moko-resource"
+
+    def get_masks(self, eager: bool = False, hint: Optional[str] = None):
+        """
+        Return all file masks found in the directory.
+
+        It is expected to contain duplicates.
+        """
+        for path in self.finder.filter_files(
+            r"(strings|plurals)\.xml", ".*/resources/mr/base"
+        ):
+            mask = list(path.parts)
+            mask[-2] = "*"
+
+            yield {"filemask": "/".join(mask), "template": path.as_posix()}
+
+
+@register_discovery
 class OSXDiscovery(EncodingDiscovery):
     """OSX string properties files discovery."""
 
     file_format = "strings-utf8"
     encoding_map = {
-        "utf-16": "strings-utf16",
+        "utf-16": "strings",
     }
 
     def get_masks(self, eager: bool = False, hint: Optional[str] = None):
-        """Return all file masks found in the directory.
+        """
+        Return all file masks found in the directory.
 
-        It is expected to contain duplicates."""
+        It is expected to contain duplicates.
+        """
         for path in self.finder.filter_files(r".*\.strings", 
r".*/(base|en)\.lproj"):
             mask = list(path.parts)
             mask[-2] = "*.lproj"
@@ -162,9 +185,11 @@
     file_format = "stringsdict"
 
     def get_masks(self, eager: bool = False, hint: Optional[str] = None):
-        """Return all file masks found in the directory.
+        """
+        Return all file masks found in the directory.
 
-        It is expected to contain duplicates."""
+        It is expected to contain duplicates.
+        """
         for path in self.finder.filter_files(
             r".*\.stringsdict", r".*/(base|en)\.lproj"
         ):
@@ -202,9 +227,11 @@
         yield from super().possible_templates(language, mask)
 
     def get_masks(self, eager: bool = False, hint: Optional[str] = None):
-        """Return all file masks found in the directory.
+        """
+        Return all file masks found in the directory.
 
-        It is expected to contain duplicates."""
+        It is expected to contain duplicates.
+        """
         for path in self.finder.filter_files(r".*\..*\.res[xw]"):
             mask = list(path.parts)
             base, code, ext = mask[-1].rsplit(".", 2)
@@ -281,9 +308,7 @@
                     detected = self.detect_dict(value, level + 1)
                     i18next |= detected == "i18next"
                     i18nextv4 |= detected == "i18nextv4"
-            elif (
-                key.endswith("_one") or key.endswith("_many") or 
key.endswith("_other")
-            ):
+            elif key.endswith(("_one", "_many", "_other")):
                 i18nextv4 = True
             elif key.endswith("_plural") or "{{" in value:
                 i18next = True
@@ -296,11 +321,11 @@
             return "json"
         return None
 
-    def adjust_format(self, result: Dict[str, str]):
+    def adjust_format(self, result: dict[str, str]):
         if "template" not in result:
             return
 
-        path = list(self.finder.mask_matches(result["template"]))[0]
+        path = next(iter(self.finder.mask_matches(result["template"])))
 
         if not hasattr(path, "open"):
             return
@@ -344,11 +369,11 @@
     file_format = "yaml"
     mask = ("*.yml", "*.yaml")
 
-    def adjust_format(self, result: Dict[str, str]):
+    def adjust_format(self, result: dict[str, str]):
         if "template" not in result:
             return
 
-        path = list(self.finder.mask_matches(result["template"]))[0]
+        path = next(iter(self.finder.mask_matches(result["template"])))
 
         if not hasattr(path, "open"):
             return
@@ -360,7 +385,7 @@
             except (YAMLError, YAMLFutureWarning):
                 return
             if isinstance(data, dict) and len(data) == 1:
-                key = list(data.keys())[0]
+                key = next(iter(data.keys()))
                 if "filemask" in result:
                     if result["filemask"].replace("*", key) == 
result["template"]:
                         result["file_format"] = "ruby-yaml"
@@ -407,11 +432,11 @@
     file_format = "php"
     mask = "*.php"
 
-    def adjust_format(self, result: Dict[str, str]):
+    def adjust_format(self, result: dict[str, str]):
         if "template" not in result:
             return
 
-        path = list(self.finder.mask_matches(result["template"]))[0]
+        path = next(iter(self.finder.mask_matches(result["template"])))
 
         if not hasattr(path, "open"):
             return
@@ -503,7 +528,7 @@
     file_format = "arb"
     mask = "*.arb"
 
-    def fill_in_new_base(self, result: Dict[str, str]):
+    def fill_in_new_base(self, result: dict[str, str]):
         super().fill_in_new_base(result)
         if "intermediate" not in result:
             # Flutter intermediate files
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/translation_finder/discovery/result.py 
new/translation-finder-2.16/translation_finder/discovery/result.py
--- old/translation-finder-2.15/translation_finder/discovery/result.py  
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/translation_finder/discovery/result.py  
2023-12-20 13:21:31.000000000 +0100
@@ -9,8 +9,7 @@
     """
     Discovery result class.
 
-    This is essentially a dict with meta dict containing additional
-    information.
+    Subclass of a dict with meta dict containing additional information.
     """
 
     def __init__(self, *args, **kwargs):
@@ -26,8 +25,8 @@
         return dict(self)
 
     def __lt__(self, other):
-        """This is only method needed for sort."""
-        return self._sort_key < other._sort_key  # noqa:SF01,SLF001
+        """Only method needed for sort."""
+        return self._sort_key < other._sort_key
 
     def __eq__(self, other):
         return super().__eq__(other) and (
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/translation_finder/discovery/transifex.py 
new/translation-finder-2.16/translation_finder/discovery/transifex.py
--- old/translation-finder-2.15/translation_finder/discovery/transifex.py       
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/translation_finder/discovery/transifex.py       
2023-12-20 13:21:31.000000000 +0100
@@ -7,7 +7,8 @@
 from configparser import RawConfigParser
 from typing import Optional
 
-from ..api import register_discovery
+from translation_finder.api import register_discovery
+
 from .base import BaseDiscovery
 
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/translation-finder-2.15/translation_finder/finder.py 
new/translation-finder-2.16/translation_finder/finder.py
--- old/translation-finder-2.15/translation_finder/finder.py    2023-01-13 
13:43:37.000000000 +0100
+++ new/translation-finder-2.16/translation_finder/finder.py    2023-12-20 
13:21:31.000000000 +0100
@@ -70,10 +70,11 @@
         return (path, relative, relative.as_posix())
 
     def list_files(self, root, files, dirs):
-        """Recursively list files and dirs in a path.
-
-        It skips excluded files."""
+        """
+        Recursively list files and dirs in a path.
 
+        It skips excluded files.
+        """
         with scandir(root) as matches:
             for path in matches:
                 if path.is_symlink():
@@ -101,6 +102,8 @@
 
     def mask_matches(self, mask: str):
         """Return all mask matches."""
+        # Avoid dealing [ as a special char
+        mask = mask.replace("[", "[[]").replace("?", "[?]")
         for name, path in self.files:
             if fnmatch(name, mask):
                 yield path
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/translation-finder-2.15/translation_finder/test_discovery.py 
new/translation-finder-2.16/translation_finder/test_discovery.py
--- old/translation-finder-2.15/translation_finder/test_discovery.py    
2023-01-13 13:43:37.000000000 +0100
+++ new/translation-finder-2.16/translation_finder/test_discovery.py    
2023-12-20 13:21:31.000000000 +0100
@@ -8,6 +8,7 @@
 from .discovery.base import DiscoveryResult
 from .discovery.files import (
     AndroidDiscovery,
+    MOKODiscovery,
     AppStoreDiscovery,
     ARBDiscovery,
     CSVDiscovery,
@@ -567,6 +568,36 @@
         )
 
 
+class MOKOTest(DiscoveryTestCase):
+    def test_basic(self):
+        discovery = MOKODiscovery(
+            self.get_finder(
+                [
+                    "app/src/res/main/values/strings.xml",
+                    "app/src/res/main/values-it/strings.xml",
+                    "app/src/res/main/values-it/strings-other.xml",
+                    "src/commonMain/resources/MR/base/strings.xml",
+                    "src/commonMain/resources/MR/base/plurals.xml",
+                ]
+            )
+        )
+        self.assert_discovery(
+            discovery.discover(),
+            [
+                {
+                    "filemask": "src/commonMain/resources/MR/*/plurals.xml",
+                    "template": "src/commonMain/resources/MR/base/plurals.xml",
+                    "file_format": "moko-resource",
+                },
+                {
+                    "filemask": "src/commonMain/resources/MR/*/strings.xml",
+                    "template": "src/commonMain/resources/MR/base/strings.xml",
+                    "file_format": "moko-resource",
+                },
+            ],
+        )
+
+
 class OSXTest(DiscoveryTestCase):
     def test_basic(self):
         discovery = OSXDiscovery(
@@ -894,6 +925,27 @@
                 },
             ],
         )
+
+    def test_shell_chars(self):
+        discovery = JSONDiscovery(
+            self.get_finder(
+                [
+                    "src/app/[locale]/_translations/en.json",
+                    "src/app/[locale]/_translations/de.json",
+                    "src/app/[locale]/_translations/cs.json",
+                ]
+            )
+        )
+        self.assert_discovery(
+            discovery.discover(),
+            [
+                {
+                    "filemask": "src/app/[locale]/_translations/*.json",
+                    "file_format": "json-nested",
+                    "template": "src/app/[locale]/_translations/en.json",
+                },
+            ],
+        )
 
     def test_json_data(self):
         """

Reply via email to