From de9783005d97542631ec16007e021e9d65614723 Mon Sep 17 00:00:00 2001 From: 0xJacky Date: Tue, 9 Dec 2025 02:58:13 +0000 Subject: [PATCH] fix: improve error handling and path resolution in license generation --- app/src/language/ja_JP/app.po | 170 ++++++++--------- app/src/language/uk_UA/app.po | 4 +- app/src/language/zh_CN/app.po | 4 +- app/src/language/zh_TW/app.po | 6 +- .../internal/license/licenses.xz | Bin 96 -> 0 bytes cmd/generate_licenses/main.go | 92 +++++++-- cmd/language_spacing/main.go | 174 ++++++++++++++++++ internal/license/licenses.xz | Bin 31616 -> 8572 bytes 8 files changed, 339 insertions(+), 111 deletions(-) delete mode 100644 cmd/generate_licenses/internal/license/licenses.xz create mode 100644 cmd/language_spacing/main.go diff --git a/app/src/language/ja_JP/app.po b/app/src/language/ja_JP/app.po index f97e9e42..b633d9a7 100644 --- a/app/src/language/ja_JP/app.po +++ b/app/src/language/ja_JP/app.po @@ -34,7 +34,7 @@ msgstr "[Nginx UI] 証明書の失効に成功しました" #: src/language/generate.ts:41 msgid "[Nginx UI] Certificate was used for server, reloading server TLS certificate" -msgstr "[Nginx UI] サーバーで証明書が使用されました、サーバーのTLS証明書を再読み込み中" +msgstr "[Nginx UI] サーバーで証明書が使用されました、サーバーのTLS 証明書を再読み込み中" #: src/language/generate.ts:42 msgid "[Nginx UI] Creating client facilitates communication with the CA server" @@ -113,7 +113,7 @@ msgstr "* グループ %{groupName} のノードと手動で選択したノー msgid "" "* Index files are stored in the \"log-index\" directory within your Nginx " "UI config path by default." -msgstr "* インデックスファイルはデフォルトでNGINX UI設定パス内の「log-index」ディレクトリに保存されます。" +msgstr "* インデックスファイルはデフォルトでNGINX UI 設定パス内の「log-index」ディレクトリに保存されます。" #: src/views/nginx_log/components/IndexingSettingsModal.vue:217 msgid "" @@ -129,7 +129,7 @@ msgstr "%{total} 項目中 %{start}~%{end}" #: src/views/nginx_log/components/IndexingSettingsModal.vue:49 msgid "1 core minimum" -msgstr "最小1コア" +msgstr "最小 1コア" #: src/views/nginx_log/components/IndexingSettingsModal.vue:55 msgid "1GB RAM minimum" @@ -142,7 +142,7 @@ msgstr "2+ コア推奨" #: src/views/nginx_log/dashboard/components/HourlyChart.vue:67 #: src/views/nginx_log/dashboard/components/HourlyChart.vue:68 msgid "24-Hour UV/PV Statistics" -msgstr "24時間UV/PV統計" +msgstr "24 時間 UV/PV 統計" #: src/views/user/userColumns.tsx:30 msgid "2FA" @@ -154,7 +154,7 @@ msgstr "ニ要素認証設定" #: src/views/nginx_log/components/IndexingSettingsModal.vue:56 msgid "4GB+ RAM recommended" -msgstr "4GB以上のRAMを推奨" +msgstr "4GB 以上のRAMを推奨" #: src/routes/modules/system.ts:38 msgid "About" @@ -392,7 +392,7 @@ msgstr "新しいリカバリーコードを生成してもよろしいですか #: src/views/preference/components/AuthSettings/TOTP.vue:87 msgid "Are you sure to reset 2FA?" -msgstr "2要素認証をリセットしてもよろしいですか?" +msgstr "2 要素認証をリセットしてもよろしいですか?" #: src/components/Notification/Notification.vue:117 #: src/views/notification/Notification.vue:40 @@ -546,7 +546,7 @@ msgstr "平均レイテンシ" #: src/views/nginx_log/dashboard/components/SummaryStats.vue:33 msgid "Avg Daily UV" -msgstr "平均日間UV" +msgstr "平均日間 UV" #: src/views/nginx_log/structured/StructuredLogViewer.vue:793 msgid "Avg/PV" @@ -844,7 +844,7 @@ msgstr "証明書 %{name} は %{days} 日後に期限切れになります" #: src/components/Notification/notifications.ts:58 msgid "Certificate %{name} will expire in 1 day" -msgstr "証明書 %{name} は1日で期限切れになります" +msgstr "証明書 %{name} は1 日で期限切れになります" #: src/views/certificate/components/CertificateDownload.vue:37 msgid "Certificate content and private key content cannot be empty" @@ -1416,11 +1416,11 @@ msgstr "CPUステータス" #: src/views/dashboard/components/ResourceUsageCard.vue:27 msgid "CPU Usage" -msgstr "CPU使用率" +msgstr "CPU 使用率" #: src/views/dashboard/components/ResourceUsageCard.vue:38 msgid "CPU usage is relatively high, consider optimizing Nginx configuration" -msgstr "CPU使用率が比較的高いため、Nginxの設定を最適化することを検討してください" +msgstr "CPU 使用率が比較的高いため、Nginxの設定を最適化することを検討してください" #: src/views/dashboard/ServerAnalytic.vue:200 msgid "CPU:" @@ -1480,7 +1480,7 @@ msgstr "認証情報" #: src/views/backup/AutoBackup/components/CronEditor.vue:194 msgid "Cron Expression" -msgstr "Cron式" +msgstr "Cron 式" #: src/views/nginx_log/components/IndexingSettingsModal.vue:266 msgid "Cross-file timeline correlation" @@ -2031,7 +2031,7 @@ msgstr "ドライランモードが有効です" msgid "" "Due to the security policies of some browsers, you cannot use passkeys on " "non-HTTPS websites, except when running on localhost." -msgstr "一部のブラウザのセキュリティポリシーのため、localhostで実行している場合を除き、非HTTPSウェブサイトではパスキーを使用できません。" +msgstr "一部のブラウザのセキュリティポリシーのため、localhostで実行している場合を除き、非 HTTPSウェブサイトではパスキーを使用できません。" #: src/components/LLM/LLMSessionTabs.vue:287 #: src/components/LLM/LLMSessionTabs.vue:378 @@ -2058,7 +2058,7 @@ msgstr "動的シャード管理" #: src/views/backup/AutoBackup/components/CronEditor.vue:197 msgid "e.g., 0 0 * * * (daily at midnight)" -msgstr "例: 0 0 * * * (毎日深夜0時)" +msgstr "例: 0 0 * * * (毎日深夜 0 時)" #: src/views/certificate/ACMEUser.vue:100 msgid "EAB HMAC Key" @@ -2436,7 +2436,7 @@ msgstr "exec インスタンスへのアタッチに失敗しました: {0}" #: src/constants/errors/backup.ts:5 msgid "Failed to backup Nginx config files: {0}" -msgstr "Nginx設定ファイルのバックアップに失敗しました: {0}" +msgstr "Nginx 設定ファイルのバックアップに失敗しました: {0}" #: src/constants/errors/backup.ts:4 msgid "Failed to backup Nginx UI files: {0}" @@ -2476,7 +2476,7 @@ msgstr "ファイルの内容のコピーに失敗しました: {0}" #: src/constants/errors/backup.ts:19 msgid "Failed to copy Nginx config directory: {0}" -msgstr "Nginx設定ディレクトリのコピーに失敗しました: {0}" +msgstr "Nginx 設定ディレクトリのコピーに失敗しました: {0}" #: src/views/certificate/components/CertificateBasicInfo.vue:33 #: src/views/certificate/components/CertificateContentEditor.vue:114 @@ -2723,7 +2723,7 @@ msgstr "ZIPファイルを開けませんでした: {0}" #: src/constants/errors/performance.ts:7 msgid "Failed to parse nginx config: {0}" -msgstr "nginx設定の解析に失敗しました: {0}" +msgstr "nginx 設定の解析に失敗しました: {0}" #: src/constants/errors/self_check.ts:5 msgid "Failed to parse nginx.conf" @@ -2787,7 +2787,7 @@ msgstr "サイトの更新に失敗しました" #: src/constants/errors/backup.ts:37 msgid "Failed to restore Nginx configs: {0}" -msgstr "Nginx設定の復元に失敗しました: {0}" +msgstr "Nginx 設定の復元に失敗しました: {0}" #: src/views/certificate/components/RemoveCert.vue:59 msgid "Failed to revoke certificate" @@ -3068,7 +3068,7 @@ msgstr "データの取得に失敗しました" #: src/constants/errors/cert.ts:12 msgid "Get dns credential error: {0}" -msgstr "DNS認証情報の取得エラー: {0}" +msgstr "DNS 認証情報の取得エラー: {0}" #: src/views/node/BatchUpgrader.vue:182 src/views/system/Upgrade.vue:188 msgid "Get release information error" @@ -3110,20 +3110,20 @@ msgid "" "gRPCS uses TLS encryption. Server must implement gRPC Health Check service. " "For testing, SSL validation is disabled by default." msgstr "" -"gRPCSはTLS暗号化を使用します。サーバーはgRPCヘルスチェックサービスを実装する必要があります。テストでは、SSL検証はデフォルトで無効になって" +"gRPCSはTLS 暗号化を使用します。サーバーはgRPCヘルスチェックサービスを実装する必要があります。テストでは、SSL 検証はデフォルトで無効になって" "います。" #: src/views/dashboard/components/ParamsOpt/PerformanceConfig.vue:67 msgid "GZIP Compression" -msgstr "GZIP圧縮" +msgstr "GZIP 圧縮" #: src/views/dashboard/components/ParamsOpt/PerformanceConfig.vue:87 msgid "GZIP Compression Level" -msgstr "GZIP圧縮レベル" +msgstr "GZIP 圧縮レベル" #: src/views/dashboard/components/ParamsOpt/PerformanceConfig.vue:80 msgid "GZIP Min Length" -msgstr "GZIP最小長" +msgstr "GZIP 最小長" #: src/views/upstream/SocketList.vue:60 msgid "Health Check" @@ -3221,7 +3221,7 @@ msgstr "https://..." #: src/views/preference/tabs/NodeSettings.vue:34 msgid "ICP Number" -msgstr "ICP番号" +msgstr "ICP 番号" #: src/views/preference/tabs/AuthSettings.vue:109 msgid "" @@ -3366,13 +3366,13 @@ msgstr "インストール" #: src/constants/errors/system.ts:3 msgid "Installation is not allowed after 10 minutes of system startup" -msgstr "システム起動後10分経過するとインストールは許可されません" +msgstr "システム起動後 10 分経過するとインストールは許可されません" #: src/views/install/components/TimeoutAlert.vue:11 msgid "" "Installation is not allowed after 10 minutes of system startup, please " "restart the Nginx UI." -msgstr "システム起動から10分後はインストールが許可されません。Nginx UIを再起動してください。" +msgstr "システム起動から10 分後はインストールが許可されません。Nginx UIを再起動してください。" #: src/views/dns/DDNSManager.vue:79 #: src/views/preference/tabs/LogrotateSettings.vue:26 @@ -3389,7 +3389,7 @@ msgstr "無効" #: src/constants/errors/backup.ts:41 msgid "Invalid AES IV format: {0}" -msgstr "無効なAES IV形式: {0}" +msgstr "無効なAES IV 形式: {0}" #: src/constants/errors/backup.ts:40 msgid "Invalid AES key format: {0}" @@ -3427,7 +3427,7 @@ msgstr "無効なフォルダ名" #: src/constants/errors/notification.ts:4 msgid "Invalid notification ID" -msgstr "無効な通知ID" +msgstr "無効な通知 ID" #: src/constants/errors/notification.ts:3 msgid "Invalid notifier config" @@ -3490,7 +3490,7 @@ msgstr "IPアドレス" #: src/components/AutoCertForm/AutoCertForm.vue:123 msgid "IP Certificate Notice" -msgstr "IP証明書の通知" +msgstr "IP 証明書の通知" #: src/views/certificate/CertificateList/Certificate.vue:37 msgid "Issue certificate" @@ -3545,41 +3545,41 @@ msgstr "Lark カスタム" #: src/views/nginx_log/structured/StructuredLogViewer.vue:315 msgid "Last 12 hours" -msgstr "過去12時間" +msgstr "過去 12 時間" #: src/views/nginx_log/dashboard/components/DateRangeSelector.vue:22 msgid "Last 14 days" -msgstr "過去14日間" +msgstr "過去 14 日間" #: src/views/nginx_log/structured/StructuredLogViewer.vue:311 msgid "Last 15 minutes" -msgstr "過去15分" +msgstr "過去 15 分" #: src/views/nginx_log/structured/StructuredLogViewer.vue:316 msgid "Last 24 hours" -msgstr "過去24時間" +msgstr "過去 24 時間" #: src/views/nginx_log/dashboard/components/DateRangeSelector.vue:23 #: src/views/nginx_log/structured/StructuredLogViewer.vue:318 msgid "Last 30 days" -msgstr "過去30日間" +msgstr "過去 30 日間" #: src/views/nginx_log/structured/StructuredLogViewer.vue:312 msgid "Last 30 minutes" -msgstr "過去30分" +msgstr "過去 30 分" #: src/views/nginx_log/structured/StructuredLogViewer.vue:314 msgid "Last 4 hours" -msgstr "過去4時間" +msgstr "過去 4 時間" #: src/views/nginx_log/dashboard/components/DateRangeSelector.vue:21 #: src/views/nginx_log/structured/StructuredLogViewer.vue:317 msgid "Last 7 days" -msgstr "過去7日間" +msgstr "過去 7 日間" #: src/views/nginx_log/dashboard/components/DateRangeSelector.vue:24 msgid "Last 90 days" -msgstr "過去90日間" +msgstr "過去 90 日間" #: src/views/backup/AutoBackup/AutoBackup.vue:190 msgid "Last Backup Status" @@ -3599,7 +3599,7 @@ msgstr "最終確認日時" #: src/views/nginx_log/structured/StructuredLogViewer.vue:313 msgid "Last hour" -msgstr "過去1時間" +msgstr "過去 1 時間" #: src/views/nginx_log/NginxLogList.vue:258 msgid "Last Indexed" @@ -4229,35 +4229,35 @@ msgstr "Nginx および Nginx UI 設定" #: src/constants/errors/self_check.ts:6 msgid "Nginx conf no http block" -msgstr "Nginx設定にhttpブロックがありません" +msgstr "Nginx 設定にhttpブロックがありません" #: src/constants/errors/self_check.ts:8 msgid "Nginx conf no stream block" -msgstr "Nginx設定にストリームブロックがありません" +msgstr "Nginx 設定にストリームブロックがありません" #: src/constants/errors/self_check.ts:15 msgid "Nginx conf not include conf.d directory" -msgstr "Nginx設定にconf.dディレクトリが含まれていません" +msgstr "Nginx 設定にconf.dディレクトリが含まれていません" #: src/constants/errors/self_check.ts:7 msgid "Nginx conf not include sites-enabled" -msgstr "Nginx設定にsites-enabledが含まれていません" +msgstr "Nginx 設定にsites-enabledが含まれていません" #: src/constants/errors/self_check.ts:9 msgid "Nginx conf not include stream-enabled" -msgstr "Nginx設定にstream-enabledが含まれていません" +msgstr "Nginx 設定にstream-enabledが含まれていません" #: src/constants/errors/backup.ts:18 msgid "Nginx config directory is not set" -msgstr "Nginx設定ディレクトリが設定されていません" +msgstr "Nginx 設定ディレクトリが設定されていません" #: src/language/generate.ts:28 msgid "Nginx configuration directory exists" -msgstr "Nginx設定ディレクトリが存在します" +msgstr "Nginx 設定ディレクトリが存在します" #: src/language/generate.ts:29 msgid "Nginx configuration entry file exists" -msgstr "Nginx設定エントリファイルが存在します" +msgstr "Nginx 設定エントリファイルが存在します" #: src/components/SystemRestore/SystemRestoreContent.vue:138 msgid "Nginx configuration has been restored" @@ -4266,7 +4266,7 @@ msgstr "Nginxの設定が復元されました" #: src/views/site/site_edit/components/SiteEditor/SiteEditor.vue:135 #: src/views/stream/components/StreamEditor.vue:105 msgid "Nginx Configuration Parse Error" -msgstr "Nginx設定解析エラー" +msgstr "Nginx 設定解析エラー" #: src/views/preference/tabs/NginxSettings.vue:22 msgid "Nginx Configuration Path" @@ -4287,7 +4287,7 @@ msgstr "Nginx 制御モード" #: src/composables/usePerformanceMetrics.ts:149 #: src/views/dashboard/components/PerformanceTablesCard.vue:105 msgid "Nginx CPU usage rate" -msgstr "NginxのCPU使用率" +msgstr "NginxのCPU 使用率" #: src/views/preference/tabs/NginxSettings.vue:16 msgid "Nginx Error Log Path" @@ -4547,7 +4547,7 @@ msgstr "まだ実行されていません" #: src/components/AutoCertForm/AutoCertForm.vue:230 msgid "Not supported for IP certificates" -msgstr "IP証明書には対応していません" +msgstr "IP 証明書には対応していません" #: src/components/CertInfo/CertInfo.vue:41 msgid "Not Valid Before: %{date}" @@ -4818,7 +4818,7 @@ msgstr "パスワードが間違っています" #: src/views/install/components/InstallForm.vue:45 msgid "Password length cannot exceed 20 characters" -msgstr "パスワードの長さは20文字を超えることはできません" +msgstr "パスワードの長さは20 文字を超えることはできません" #: src/views/user/UserProfile.vue:96 msgid "Password updated successfully" @@ -4963,13 +4963,13 @@ msgstr "すべての項目を正しく入力してください" #: src/views/backup/AutoBackup/components/StorageConfigEditor.vue:23 msgid "Please fill in required S3 configuration fields" -msgstr "必要なS3設定項目を入力してください" +msgstr "必要なS3 設定項目を入力してください" #: src/views/dns/DNSCredential.vue:93 msgid "" "Please fill in the API authentication credentials provided by your DNS " "provider." -msgstr "DNSプロバイダーから提供されたAPI認証情報を入力してください。" +msgstr "DNSプロバイダーから提供されたAPI 認証情報を入力してください。" #: src/components/AutoCertForm/AutoCertForm.vue:168 msgid "" @@ -5202,7 +5202,7 @@ msgstr "プロキシターゲット" #: src/components/AutoCertForm/AutoCertForm.vue:192 msgid "Public CA Requirements:" -msgstr "公開CAの要件:" +msgstr "公開 CAの要件:" #: src/views/preference/tabs/NodeSettings.vue:46 msgid "Public Security Number" @@ -5644,7 +5644,7 @@ msgstr "バックアップから復元" #: src/components/SystemRestore/SystemRestoreContent.vue:223 #: src/components/SystemRestore/SystemRestoreContent.vue:300 msgid "Restore Nginx Configuration" -msgstr "Nginx設定を復元" +msgstr "Nginx 設定を復元" #: src/components/SystemRestore/SystemRestoreContent.vue:234 #: src/components/SystemRestore/SystemRestoreContent.vue:311 @@ -5737,15 +5737,15 @@ msgstr "S3バケット名" #: src/constants/errors/backup.ts:56 msgid "S3 configuration is incomplete: missing {0}" -msgstr "S3設定が不完全です: {0}が不足しています" +msgstr "S3 設定が不完全です: {0}が不足しています" #: src/views/backup/AutoBackup/components/StorageConfigEditor.vue:34 msgid "S3 connection test failed" -msgstr "S3接続テストが失敗しました" +msgstr "S3 接続テストが失敗しました" #: src/views/backup/AutoBackup/components/StorageConfigEditor.vue:30 msgid "S3 connection test successful" -msgstr "S3接続テストが成功しました" +msgstr "S3 接続テストが成功しました" #: src/views/backup/AutoBackup/AutoBackup.vue:243 #: src/views/backup/AutoBackup/components/StorageConfigEditor.vue:66 @@ -6121,7 +6121,7 @@ msgstr "パスキーでサインイン" #: src/views/nginx_log/components/IndexingSettingsModal.vue:76 msgid "SIMD-optimized stream processing" -msgstr "SIMD最適化されたストリーム処理" +msgstr "SIMD 最適化されたストリーム処理" #: src/components/NgxConfigEditor/directive/DirectiveAdd.vue:48 msgid "Single Directive" @@ -6205,7 +6205,7 @@ msgstr "並べ替え基準" #: src/views/dashboard/components/SiteHealthCheckModal.vue:683 msgid "Source IP" -msgstr "送信元IP" +msgstr "送信元 IP" #: src/views/system/About.vue:46 msgid "Sponsor" @@ -6218,33 +6218,33 @@ msgstr "I/O パフォーマンス向上のための SSD ストレージ" #: src/views/certificate/components/CertificateContentEditor.vue:209 #: src/views/certificate/components/CertificateContentEditor.vue:214 msgid "SSL Certificate Content" -msgstr "SSL証明書の内容" +msgstr "SSL 証明書の内容" #: src/constants/errors/system.ts:8 msgid "SSL certificate file must be under Nginx configuration directory: {0}" -msgstr "SSL証明書ファイルはNginx設定ディレクトリの下にある必要があります: {0}" +msgstr "SSL 証明書ファイルはNginx 設定ディレクトリの下にある必要があります: {0}" #: src/constants/errors/system.ts:6 msgid "SSL certificate file not found" -msgstr "SSL証明書ファイルが見つかりません" +msgstr "SSL 証明書ファイルが見つかりません" #: src/views/certificate/components/CertificateContentEditor.vue:270 #: src/views/certificate/components/CertificateContentEditor.vue:275 msgid "SSL Certificate Key Content" -msgstr "SSL証明書キーの内容" +msgstr "SSL 証明書キーの内容" #: src/views/certificate/components/CertificateBasicInfo.vue:112 #: src/views/certificate/components/CertificateBasicInfo.vue:126 #: src/views/certificate/components/CertificateBasicInfo.vue:138 msgid "SSL Certificate Key Path" -msgstr "SSL証明書キーパス" +msgstr "SSL 証明書キーパス" #: src/views/certificate/components/CertificateBasicInfo.vue:104 #: src/views/certificate/components/CertificateBasicInfo.vue:78 #: src/views/certificate/components/CertificateBasicInfo.vue:92 #: src/views/preference/tabs/ServerSettings.vue:37 msgid "SSL Certificate Path" -msgstr "SSL証明書のパス" +msgstr "SSL 証明書のパス" #: src/constants/errors/system.ts:4 msgid "SSL certificate path is required when HTTPS is enabled" @@ -6252,7 +6252,7 @@ msgstr "HTTPS を有効にするには SSL 証明書のパスが必要です" #: src/constants/errors/system.ts:9 msgid "SSL key file must be under Nginx configuration directory: {0}" -msgstr "SSLキーファイルはNginx設定ディレクトリの下にある必要があります: {0}" +msgstr "SSLキーファイルはNginx 設定ディレクトリの下にある必要があります: {0}" #: src/constants/errors/system.ts:7 msgid "SSL key file not found" @@ -6579,7 +6579,7 @@ msgstr "テストメッセージが正常に送信されました" #: src/views/backup/AutoBackup/components/StorageConfigEditor.vue:141 msgid "Test S3 Connection" -msgstr "S3接続をテスト" +msgstr "S3 接続をテスト" #: src/views/dashboard/components/SiteHealthCheckModal.vue:448 msgid "Test successful! Response time: %{response_time}ms" @@ -6590,7 +6590,7 @@ msgid "" "The certificate for the domain will be checked 30 minutes, and will be " "renewed if it has been more than 1 week or the period you set in settings " "since it was last issued." -msgstr "ドメインの証明書は30分ごとにチェックされ、最後に発行されてから1週間以上経過しているか、設定で指定した期間が経過している場合に更新されます。" +msgstr "ドメインの証明書は30 分ごとにチェックされ、最後に発行されてから1 週間以上経過しているか、設定で指定した期間が経過している場合に更新されます。" #: src/components/GeoLiteDownload/GeoLiteDownload.vue:158 msgid "" @@ -6608,15 +6608,15 @@ msgstr "GeoLite2 データベースは、IP アドレスの地理情報を提供 msgid "" "The ICP Number should only contain letters, unicode, numbers, hyphens, " "dashes, colons, and dots." -msgstr "ICP番号には、文字、Unicode、数字、ハイフン、ダッシュ、コロン、およびドットのみを含める必要があります。" +msgstr "ICP 番号には、文字、Unicode、数字、ハイフン、ダッシュ、コロン、およびドットのみを含める必要があります。" #: src/views/certificate/components/CertificateContentEditor.vue:205 msgid "The input is not a SSL Certificate" -msgstr "入力はSSL証明書ではありません" +msgstr "入力はSSL 証明書ではありません" #: src/views/certificate/components/CertificateContentEditor.vue:266 msgid "The input is not a SSL Certificate Key" -msgstr "入力はSSL証明書キーではありません" +msgstr "入力はSSL 証明書キーではありません" #: src/constants/errors/nginx_log.ts:2 msgid "" @@ -6694,7 +6694,7 @@ msgstr "理論上の最大同時接続数:" #: src/views/dashboard/components/PerformanceTablesCard.vue:189 msgid "Theoretical maximum RPS (Requests Per Second):" -msgstr "理論上の最大RPS(リクエスト/秒):" +msgstr "理論上の最大 RPS(リクエスト/秒):" #: src/views/preference/components/AuthSettings/RecoveryCodes.vue:105 msgid "" @@ -6741,13 +6741,13 @@ msgstr "このフィールドは空にできません" #: src/constants/form_errors.ts:6 msgid "This field should only contain letters, unicode characters, numbers, and -_." -msgstr "このフィールドには、文字、Unicode文字、数字、および -_ のみを含める必要があります。" +msgstr "このフィールドには、文字、Unicode 文字、数字、および -_ のみを含める必要があります。" #: src/language/curd.ts:46 msgid "" "This field should only contain letters, unicode characters, numbers, and " "-_./:" -msgstr "このフィールドには、文字、Unicode文字、数字、および -_./: のみを含める必要があります" +msgstr "このフィールドには、文字、Unicode 文字、数字、および -_./: のみを含める必要があります" #: src/components/Notification/notifications.ts:94 msgid "This is a test message sent at %{timestamp} from Nginx UI." @@ -6780,7 +6780,7 @@ msgid "" "may not be available with all ACME providers." msgstr "" "このサイトはHTTPS(ポート443)のデフォルトサーバー(default_" -"server)として設定されています。IP証明書には認証局(CA)のサポートが必要であり、すべてのACMEプロバイダーで利用可能とは限りません。" +"server)として設定されています。IP 証明書には認証局(CA)のサポートが必要であり、すべてのACMEプロバイダーで利用可能とは限りません。" #: src/components/AutoCertForm/AutoCertForm.vue:132 msgid "" @@ -6789,7 +6789,7 @@ msgid "" "support and may not be available with all ACME providers." msgstr "" "このサイトはワイルドカードサーバー名(_" -")を使用しており、通常はIPベースの証明書を示しています。IP証明書には認証局(CA)のサポートが必要であり、すべてのACMEプロバイダーで利用可能では" +")を使用しており、通常はIPベースの証明書を示しています。IP 証明書には認証局(CA)のサポートが必要であり、すべてのACMEプロバイダーで利用可能では" "ない場合があります。" #: src/views/backup/components/BackupCreator.vue:141 @@ -6823,7 +6823,7 @@ msgstr "この特定のファイルのインデックスデータを再構築し msgid "" "This will restore all Nginx configuration files. Nginx will restart after " "the restoration is complete." -msgstr "これにより、すべてのNginx設定ファイルが復元されます。復元が完了すると、Nginxが再起動します。" +msgstr "これにより、すべてのNginx 設定ファイルが復元されます。復元が完了すると、Nginxが再起動します。" #: src/components/SystemRestore/SystemRestoreContent.vue:238 #: src/components/SystemRestore/SystemRestoreContent.vue:315 @@ -6976,7 +6976,7 @@ msgstr "Nginxプロセスの合計" #: src/views/nginx_log/dashboard/components/SummaryStats.vue:24 msgid "Total PV" -msgstr "総PV" +msgstr "総 PV" #: src/views/dashboard/ServerAnalytic.vue:284 msgid "Total Receive" @@ -7248,7 +7248,7 @@ msgstr "ユーザー名 (*)" #: src/views/install/components/InstallForm.vue:35 msgid "Username length cannot exceed 255 characters" -msgstr "ユーザー名の長さは255文字を超えることはできません" +msgstr "ユーザー名の長さは255 文字を超えることはできません" #: src/views/nginx_log/structured/StructuredLogViewer.vue:775 msgid "UV" @@ -7262,7 +7262,7 @@ msgstr "有効" #: src/views/dashboard/components/SiteHealthCheckModal.vue:658 msgid "Validate SSL Certificate" -msgstr "SSL証明書を検証" +msgstr "SSL 証明書を検証" #: src/views/dashboard/components/PerformanceTablesCard.vue:22 #: src/views/dns/components/DNSRecordForm.vue:66 @@ -7375,7 +7375,7 @@ msgstr "WebAuthn 設定が構成されていません" #: src/views/certificate/components/RemoveCert.vue:65 msgid "WebSocket connection error" -msgstr "WebSocket接続エラー" +msgstr "WebSocket 接続エラー" #: src/views/preference/components/ExternalNotify/wecom.ts:5 msgid "WeCom" @@ -7484,7 +7484,7 @@ msgstr "はい" msgid "" "You are accessing this terminal over an insecure HTTP connection on a " "non-localhost domain. This may expose sensitive information." -msgstr "あなたは非localhostドメインで安全でないHTTP接続を介してこのターミナルにアクセスしています。これにより機密情報が漏洩する可能性があります。" +msgstr "あなたは非 localhostドメインで安全でないHTTP 接続を介してこのターミナルにアクセスしています。これにより機密情報が漏洩する可能性があります。" #: src/constants/errors/config.ts:8 msgid "You are not allowed to delete a file outside of the nginx config path" @@ -7572,7 +7572,7 @@ msgstr "ゼロアロケーションパイプライン" #~ msgstr "M2 Pro(12コア)でのテストに基づく" #~ msgid "CPU Utilization" -#~ msgstr "CPU使用率" +#~ msgstr "CPU 使用率" #~ msgid "Indexing Throughput" #~ msgstr "インデックス処理能力" @@ -7656,7 +7656,7 @@ msgstr "ゼロアロケーションパイプライン" #~ msgstr "S3バケットへのアクセスが拒否されました: {0}" #~ msgid "S3 connection test failed: {0}" -#~ msgstr "S3接続テストが失敗しました: {0}" +#~ msgstr "S3 接続テストが失敗しました: {0}" #~ msgid "S3 credentials are invalid: {0}" #~ msgstr "S3の認証情報が無効です: {0}" @@ -7751,7 +7751,7 @@ msgstr "ゼロアロケーションパイプライン" #~ msgstr "両方の設定" #~ msgid "Nginx Config" -#~ msgstr "Nginx設定" +#~ msgstr "Nginx 設定" #~ msgid "Nginx UI Config" #~ msgstr "Nginx UI 設定" diff --git a/app/src/language/uk_UA/app.po b/app/src/language/uk_UA/app.po index 3f4800d1..cfc3753a 100644 --- a/app/src/language/uk_UA/app.po +++ b/app/src/language/uk_UA/app.po @@ -1579,7 +1579,7 @@ msgstr "" " JP: \"Reactを使う\" → \"React を使う\"\n" " KO: \"Node.js설치\" → \"Node.js 설치\"\n" " TH: \"ติดตั้งPython3.9\" → \"ติดตั้ง Python 3.9\"\n" -" - Винятки: числа/одиниці/оператори (200GB硬盘 → 200GB 硬盘)\n" +" - Винятки: числа/одиниці/оператори (200GB 硬盘 → 200GB 硬盘)\n" "\n" "# Вихідні дані\n" " - Повертати лише результат перекладу\n" @@ -1838,7 +1838,7 @@ msgstr "" " JP: \"Reactを使う\" → \"React を使う\"\n" " KO: \"Node.js설치\" → \"Node.js 설치\"\n" " TH: \"ติดตั้งPython3.9\" → \"ติดตั้ง Python 3.9\"\n" -" - Винятки: числа/одиниці/оператори (200GB硬盘 → 200GB 硬盘)\n" +" - Винятки: числа/одиниці/оператори (200GB 硬盘 → 200GB 硬盘)\n" "\n" "# Вихідні дані:\n" " - Повертати лише результат перекладу\n" diff --git a/app/src/language/zh_CN/app.po b/app/src/language/zh_CN/app.po index 1ea1e11f..02c7116a 100644 --- a/app/src/language/zh_CN/app.po +++ b/app/src/language/zh_CN/app.po @@ -1891,7 +1891,7 @@ msgstr "DNS 域名" #: src/views/dns/components/DNSRecordTable.vue:81 msgid "DNS Only" -msgstr "仅DNS" +msgstr "仅 DNS" #: src/components/AutoCertForm/DNSChallenge.vue:121 #: src/views/dns/components/DNSChallenge.vue:60 @@ -7107,7 +7107,7 @@ msgstr "升级器核心摘要为空" #: src/constants/errors/upgrader.ts:2 msgid "Upgrader core downloadUrl is empty" -msgstr "升级器核心下载URL为空" +msgstr "升级器核心下载 URL 为空" #: src/views/node/BatchUpgrader.vue:88 src/views/system/Upgrade.vue:80 msgid "Upgrading Nginx UI, please wait..." diff --git a/app/src/language/zh_TW/app.po b/app/src/language/zh_TW/app.po index 51e485ce..62d80980 100644 --- a/app/src/language/zh_TW/app.po +++ b/app/src/language/zh_TW/app.po @@ -1895,7 +1895,7 @@ msgstr "DNS 網域" #: src/views/dns/components/DNSRecordTable.vue:81 msgid "DNS Only" -msgstr "僅DNS" +msgstr "僅 DNS" #: src/components/AutoCertForm/DNSChallenge.vue:121 #: src/views/dns/components/DNSChallenge.vue:60 @@ -4128,7 +4128,7 @@ msgstr "命名空間" msgid "" "Need more DNS providers? Support us through donations or contact us for " "commercial collaboration" -msgstr "需要更多DNS供應商?透過捐贈支持我們或聯繫我們進行商業合作" +msgstr "需要更多 DNS 供應商?透過捐贈支持我們或聯繫我們進行商業合作" #: src/views/dashboard/NginxDashBoard.vue:195 msgid "Need to enable the stub_status module" @@ -7113,7 +7113,7 @@ msgstr "升級器核心摘要為空" #: src/constants/errors/upgrader.ts:2 msgid "Upgrader core downloadUrl is empty" -msgstr "升級器核心下載URL為空" +msgstr "升級器核心下載 URL 為空" #: src/views/node/BatchUpgrader.vue:88 src/views/system/Upgrade.vue:80 msgid "Upgrading Nginx UI, please wait..." diff --git a/cmd/generate_licenses/internal/license/licenses.xz b/cmd/generate_licenses/internal/license/licenses.xz deleted file mode 100644 index 16c1e55b2ace36a8367704adbdab46da593110ab..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 96 zcmV-m0H6Q;H+ooF000E$*0e?f03iVu0001VFXf})04M+>T>w3TfEOGnjR;2`dpw)1@f000001X)^3 C*CCGp diff --git a/cmd/generate_licenses/main.go b/cmd/generate_licenses/main.go index 5f4d18e6..374bbdfc 100644 --- a/cmd/generate_licenses/main.go +++ b/cmd/generate_licenses/main.go @@ -34,10 +34,16 @@ type ComponentInfo struct { func main() { log.Println("Generating license information...") + repoRoot, err := locateRepoRoot() + if err != nil { + log.Fatalf("Error locating repository root: %v", err) + } + log.Printf("INFO: Repository root resolved to %s", repoRoot) + var info ComponentInfo // Generate backend licenses - backendLicenses, err := generateBackendLicenses() + backendLicenses, err := generateBackendLicenses(repoRoot) if err != nil { log.Printf("Error generating backend licenses: %v", err) } else { @@ -46,7 +52,7 @@ func main() { } // Generate frontend licenses - frontendLicenses, err := generateFrontendLicenses() + frontendLicenses, err := generateFrontendLicenses(repoRoot) if err != nil { log.Printf("Error generating frontend licenses: %v", err) } else { @@ -83,7 +89,7 @@ func main() { compressed.Len(), float64(compressed.Len())/float64(len(jsonData))*100) // Write compressed data to file - outputPath := "internal/license/licenses.xz" + outputPath := filepath.Join(repoRoot, "internal", "license", "licenses.xz") log.Printf("INFO: Writing compressed data to %s", outputPath) err = os.MkdirAll(filepath.Dir(outputPath), 0755) if err != nil { @@ -103,16 +109,19 @@ func main() { log.Printf(" - Output file: %s", outputPath) } -func generateBackendLicenses() ([]License, error) { +func generateBackendLicenses(repoRoot string) ([]License, error) { var licenses []License log.Println("INFO: Collecting backend Go modules...") - // Read go.mod file directly - goModPath := "go.mod" + goModPath := filepath.Join(repoRoot, "go.mod") + if _, err := os.Stat(goModPath); err != nil { + return nil, fmt.Errorf("failed to locate go.mod at %s: %v", goModPath, err) + } + data, err := os.ReadFile(goModPath) if err != nil { - return nil, fmt.Errorf("failed to read go.mod: %v", err) + return nil, fmt.Errorf("failed to read go.mod at %s: %v", goModPath, err) } // Parse go.mod content to extract dependencies @@ -120,12 +129,12 @@ func generateBackendLicenses() ([]License, error) { lines := strings.Split(string(data), "\n") inRequireBlock := false inReplaceBlock := false - + replaceMap := make(map[string]string) // original -> replacement for _, line := range lines { line = strings.TrimSpace(line) - + // Handle require block if strings.HasPrefix(line, "require (") { inRequireBlock = true @@ -148,10 +157,10 @@ func generateBackendLicenses() ([]License, error) { if len(parts) == 2 { original := strings.TrimSpace(parts[0]) replacement := strings.TrimSpace(parts[1]) - + // Remove "replace " prefix if present original = strings.TrimPrefix(original, "replace ") - + // Extract module path (before version if present) if strings.Contains(original, " ") { original = strings.Fields(original)[0] @@ -159,7 +168,7 @@ func generateBackendLicenses() ([]License, error) { if strings.Contains(replacement, " ") { replacement = strings.Fields(replacement)[0] } - + replaceMap[original] = replacement } } @@ -170,13 +179,13 @@ func generateBackendLicenses() ([]License, error) { if inRequireBlock || strings.HasPrefix(line, "require ") { // Remove "require " prefix if present line = strings.TrimPrefix(line, "require ") - + // Remove comments if idx := strings.Index(line, "//"); idx != -1 { line = line[:idx] } line = strings.TrimSpace(line) - + if line == "" { continue } @@ -186,16 +195,16 @@ func generateBackendLicenses() ([]License, error) { if len(parts) >= 2 { path := parts[0] version := parts[1] - + if path == "" { continue } - + // Apply replacements if they exist if replacement, exists := replaceMap[path]; exists { path = replacement } - + depMap[path] = version } } @@ -303,13 +312,13 @@ func generateBackendLicenses() ([]License, error) { return licenses, nil } -func generateFrontendLicenses() ([]License, error) { +func generateFrontendLicenses(repoRoot string) ([]License, error) { var licenses []License log.Println("INFO: Collecting frontend npm packages...") // Read package.json - packagePath := "app/package.json" + packagePath := filepath.Join(repoRoot, "app", "package.json") if _, err := os.Stat(packagePath); os.IsNotExist(err) { return nil, fmt.Errorf("package.json not found at %s", packagePath) } @@ -760,3 +769,48 @@ func getGoVersion() string { return "Unknown" } + +// locateRepoRoot returns the directory containing go.mod so relative paths stay stable. +func locateRepoRoot() (string, error) { + goModPath, err := locateGoModPath() + if err != nil { + return "", err + } + return filepath.Dir(goModPath), nil +} + +// locateGoModPath finds the module root so the tool works from any working directory. +func locateGoModPath() (string, error) { + // Prefer go env GOMOD which respects module-aware mode. + cmd := exec.Command("go", "env", "GOMOD") + output, err := cmd.Output() + if err == nil { + path := strings.TrimSpace(string(output)) + if path != "" { + if _, statErr := os.Stat(path); statErr == nil { + return path, nil + } + } + } + + // Fallback: walk upwards from the current working directory. + dir, err := os.Getwd() + if err != nil { + return "", err + } + + for { + candidate := filepath.Join(dir, "go.mod") + if info, statErr := os.Stat(candidate); statErr == nil && !info.IsDir() { + return candidate, nil + } + + parent := filepath.Dir(dir) + if parent == dir { + break + } + dir = parent + } + + return "", fmt.Errorf("go.mod not found from current directory or parents") +} diff --git a/cmd/language_spacing/main.go b/cmd/language_spacing/main.go new file mode 100644 index 00000000..6692c772 --- /dev/null +++ b/cmd/language_spacing/main.go @@ -0,0 +1,174 @@ +//go:generate go run . +package main + +import ( + "flag" + "fmt" + "log" + "os" + "path/filepath" + "runtime" + "strings" + "unicode" +) + +type fileReport struct { + path string + insertions int +} + +var ( + dryRun = flag.Bool("dry-run", false, "only report issues without modifying files") + targetDir string + rootDir string +) + +func main() { + flag.Parse() + log.SetFlags(0) + + if err := resolvePaths(); err != nil { + log.Fatalf("resolve paths: %v", err) + } + + reports, totalInsertions, err := processDirectory(*dryRun) + if err != nil { + log.Fatalf("scan failed: %v", err) + } + + if len(reports) == 0 { + log.Println("No spacing issues detected.") + return + } + + for _, r := range reports { + relative := r.path + if rel, err := filepath.Rel(rootDir, r.path); err == nil { + relative = rel + } + fmt.Printf("%s: inserted %d space(s)\n", relative, r.insertions) + } + + if *dryRun { + log.Printf("Dry run complete. %d potential insertion(s) across %d file(s).", totalInsertions, len(reports)) + return + } + + log.Printf("Completed fixes. Inserted %d space(s) across %d file(s).", totalInsertions, len(reports)) +} + +func resolvePaths() error { + _, file, _, ok := runtime.Caller(0) + if !ok { + return fmt.Errorf("unable to determine caller") + } + + rootDir = filepath.Clean(filepath.Join(filepath.Dir(file), "../..")) + targetDir = filepath.Join(rootDir, "app/src/language") + + info, err := os.Stat(targetDir) + if err != nil { + return fmt.Errorf("stat language directory: %w", err) + } + if !info.IsDir() { + return fmt.Errorf("language path is not a directory: %s", targetDir) + } + return nil +} + +func processDirectory(dryRun bool) ([]fileReport, int, error) { + reports := make([]fileReport, 0) + totalInsertions := 0 + + err := filepath.Walk(targetDir, func(path string, info os.FileInfo, err error) error { + if err != nil { + return err + } + if info.IsDir() { + return nil + } + if !isSupportedFile(path) { + return nil + } + + original, err := os.ReadFile(path) + if err != nil { + return fmt.Errorf("read %s: %w", path, err) + } + + fixed, insertions := fixContent(string(original)) + if insertions == 0 { + return nil + } + + if !dryRun { + if err := os.WriteFile(path, []byte(fixed), info.Mode().Perm()); err != nil { + return fmt.Errorf("write %s: %w", path, err) + } + } + + reports = append(reports, fileReport{ + path: path, + insertions: insertions, + }) + totalInsertions += insertions + return nil + }) + + return reports, totalInsertions, err +} + +func isSupportedFile(path string) bool { + switch strings.ToLower(filepath.Ext(path)) { + case ".po", ".pot", ".ts": + return true + default: + return false + } +} + +func fixContent(text string) (string, int) { + runes := []rune(text) + if len(runes) == 0 { + return text, 0 + } + + var builder strings.Builder + builder.Grow(len(runes) + 16) + insertions := 0 + + for i := 0; i < len(runes); i++ { + current := runes[i] + builder.WriteRune(current) + + if i == len(runes)-1 { + break + } + + next := runes[i+1] + if needsSpace(current, next) { + builder.WriteRune(' ') + insertions++ + } + } + + return builder.String(), insertions +} + +func needsSpace(left, right rune) bool { + if isHan(left) && isASCIIAlphaNum(right) { + return true + } + if isASCIIAlphaNum(left) && isHan(right) { + return true + } + return false +} + +func isHan(r rune) bool { + return unicode.Is(unicode.Han, r) +} + +func isASCIIAlphaNum(r rune) bool { + return r <= unicode.MaxASCII && ((r >= 'a' && r <= 'z') || (r >= 'A' && r <= 'Z') || (r >= '0' && r <= '9')) +} diff --git a/internal/license/licenses.xz b/internal/license/licenses.xz index 603eaf11dd65d25af545b35d3c6f944da92c01e0..ce24f1ed0b0848ad8e9db47818905414e6d6fd7c 100644 GIT binary patch delta 8508 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

8tV12c58d4qFd9Nc+ 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 PvBYQl0ssI200dcDW!-x*