Skip to content

Commit 480056a

Browse files
authored
Merge pull request #1897 from Cihatata/sync-string-from-poeditor
feat: Sync strings from poeditor with github workflow
2 parents 7c369e8 + c50b45f commit 480056a

File tree

3 files changed

+224
-0
lines changed

3 files changed

+224
-0
lines changed
+92
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,92 @@
1+
import axios from 'axios';
2+
import fs from 'fs-extra';
3+
import path from 'path';
4+
import { fileURLToPath } from 'url';
5+
6+
// Get current directory
7+
const __filename = fileURLToPath(import.meta.url);
8+
9+
// POEditor API information
10+
const API_TOKEN = process.env.POEDITOR_API;
11+
const PROJECT_ID = process.env.POEDITOR_PROJECT_ID;
12+
const LANGUAGES = (process.env.LANGUAGES || 'tr,en').split(',');
13+
const EXPORT_FORMAT = process.env.EXPORT_FORMAT || 'key_value_json';
14+
15+
// POEditor API endpoint
16+
const API_URL = 'https://api.poeditor.com/v2';
17+
18+
// Function to download translations
19+
async function downloadTranslations() {
20+
try {
21+
console.log('Downloading translations from POEditor...');
22+
console.log(`Using export format: ${EXPORT_FORMAT}`);
23+
24+
for (const language of LANGUAGES) {
25+
console.log(`Downloading translations for ${language} language...`);
26+
27+
// Get export URL from POEditor
28+
const exportResponse = await axios.post(`${API_URL}/projects/export`,
29+
new URLSearchParams({
30+
api_token: API_TOKEN,
31+
id: PROJECT_ID,
32+
language: language,
33+
type: EXPORT_FORMAT
34+
})
35+
);
36+
37+
if (exportResponse.data.response.status !== 'success') {
38+
throw new Error(`Failed to get export URL for ${language} language: ${JSON.stringify(exportResponse.data)}`);
39+
}
40+
41+
const fileUrl = exportResponse.data.result.url;
42+
console.log(`Export URL obtained for ${language}`);
43+
44+
// Download translation file
45+
const downloadResponse = await axios.get(fileUrl, { responseType: 'json' });
46+
const translations = downloadResponse.data;
47+
console.log(`Downloaded translations for ${language}`);
48+
49+
// Check the format of data returned from POEditor and convert if necessary
50+
let formattedTranslations = translations;
51+
52+
// If data is in array format, convert it to key-value format
53+
if (Array.isArray(translations)) {
54+
console.log(`Converting array format to key-value format for ${language}`);
55+
formattedTranslations = {};
56+
translations.forEach(item => {
57+
if (item.term && item.definition) {
58+
formattedTranslations[item.term] = item.definition;
59+
}
60+
});
61+
}
62+
63+
// Save file
64+
const outputPath = path.join(process.cwd(), 'temp', `${language}.json`);
65+
await fs.writeJson(outputPath, formattedTranslations, { spaces: 2 });
66+
67+
console.log(`Translations for ${language} language successfully downloaded and saved: ${outputPath}`);
68+
}
69+
70+
console.log('All translations successfully downloaded!');
71+
} catch (error) {
72+
console.error('An error occurred while downloading translations:', error);
73+
process.exit(1);
74+
}
75+
}
76+
77+
// Main function
78+
async function main() {
79+
try {
80+
// Clean temp folder
81+
await fs.emptyDir(path.join(process.cwd(), 'temp'));
82+
83+
// Download translations
84+
await downloadTranslations();
85+
} catch (error) {
86+
console.error('An error occurred during the process:', error);
87+
process.exit(1);
88+
}
89+
}
90+
91+
// Run script
92+
main();

.github/workflows/README.md

+41
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
# POEditor Translation Synchronization
2+
3+
This GitHub Actions workflow automatically downloads translation files from POEditor and integrates them into the project.
4+
5+
## How It Works
6+
7+
The workflow can be triggered in two ways:
8+
9+
1. **Manual Trigger**: You can manually run the "POEditor Translation Synchronization" workflow from the "Actions" tab in the GitHub interface.
10+
2. **Automatic Trigger**: The workflow runs automatically every day at midnight (UTC).
11+
12+
## Required Settings
13+
14+
For this workflow to function, you need to define the following secrets in your GitHub repository:
15+
16+
1. `POEDITOR_API_TOKEN`: Your POEditor API token
17+
2. `POEDITOR_PROJECT_ID`: Your POEditor project ID
18+
19+
You can add these secrets in the "Settings > Secrets and variables > Actions" section of your GitHub repository.
20+
21+
## Manual Execution
22+
23+
When running the workflow manually, you can specify which languages to download. Languages should be entered as comma-separated values (e.g., `tr,gb,es`).
24+
25+
If you don't specify any languages, the default languages `tr` and `en` will be downloaded.
26+
27+
## Output
28+
29+
When the workflow completes successfully:
30+
31+
1. Translation files for the specified languages are downloaded from POEditor
32+
2. These files are copied to the `src/locales/` directory
33+
3. Changes are automatically committed and pushed to the main branch
34+
35+
## Troubleshooting
36+
37+
If the workflow fails:
38+
39+
1. Check the GitHub Actions logs
40+
2. Make sure your POEditor API token and project ID are correct
41+
3. Ensure that the languages you specified exist in your POEditor project

.github/workflows/poeditor-sync.yml

+91
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,91 @@
1+
name: POEditor Translation Synchronization
2+
3+
on:
4+
# For manual triggering
5+
workflow_dispatch:
6+
inputs:
7+
languages:
8+
description: "Languages to synchronize (comma separated, e.g.: tr,en,es)"
9+
required: false
10+
default: "tr,en"
11+
format:
12+
description: "Export format (key_value_json or json)"
13+
required: false
14+
default: "key_value_json"
15+
16+
# For automatic execution at a specific time (every day at midnight)
17+
schedule:
18+
- cron: "0 0 * * *"
19+
20+
jobs:
21+
sync-translations:
22+
runs-on: ubuntu-latest
23+
24+
steps:
25+
- name: Checkout code
26+
uses: actions/checkout@v3
27+
with:
28+
token: ${{ secrets.GITHUB_TOKEN }}
29+
30+
- name: Setup Node.js
31+
uses: actions/setup-node@v3
32+
with:
33+
node-version: "18"
34+
35+
- name: Create package.json for scripts
36+
run: |
37+
mkdir -p .github/scripts
38+
cat > .github/scripts/package.json << EOF
39+
{
40+
"name": "poeditor-scripts",
41+
"version": "1.0.0",
42+
"private": true,
43+
"dependencies": {
44+
"axios": "^1.6.0",
45+
"fs-extra": "^11.1.1"
46+
}
47+
}
48+
EOF
49+
50+
- name: Install dependencies
51+
run: |
52+
cd .github/scripts
53+
npm install
54+
55+
- name: Download translations from POEditor
56+
env:
57+
POEDITOR_API_TOKEN: ${{ secrets.POEDITOR_API_TOKEN }}
58+
POEDITOR_PROJECT_ID: ${{ secrets.POEDITOR_PROJECT_ID }}
59+
LANGUAGES: ${{ github.event.inputs.languages || 'tr,en' }}
60+
EXPORT_FORMAT: ${{ github.event.inputs.format || 'key_value_json' }}
61+
run: |
62+
mkdir -p temp
63+
node .github/scripts/download-translations.js
64+
65+
- name: Verify translation files
66+
run: |
67+
echo "Verifying translation files..."
68+
for file in temp/*.json; do
69+
echo "Checking $file"
70+
if [ ! -s "$file" ]; then
71+
echo "Error: $file is empty or does not exist"
72+
exit 1
73+
fi
74+
# Validate JSON format
75+
cat "$file" | jq . > /dev/null || { echo "Error: $file is not valid JSON"; exit 1; }
76+
done
77+
echo "All translation files are valid"
78+
79+
- name: Copy translations to project
80+
run: |
81+
mkdir -p src/locales
82+
cp -r temp/* src/locales/
83+
echo "Translation files copied to src/locales/"
84+
85+
- name: Commit changes
86+
run: |
87+
git config --local user.email "github-actions[bot]@users.noreply.github.com"
88+
git config --local user.name "github-actions[bot]"
89+
git add src/locales/*.json
90+
git diff --staged --quiet || git commit -m "Translations updated from POEditor"
91+
git push

0 commit comments

Comments
 (0)