feat: install svelte-18n and init setup

This commit is contained in:
Restray 2022-04-01 22:50:55 +02:00
parent 986c5b7133
commit 741db1778b
No known key found for this signature in database
GPG Key ID: 67C6DEF95A4DC812
7 changed files with 525 additions and 375 deletions

7
.vscode/settings.json vendored Normal file
View File

@ -0,0 +1,7 @@
{
"i18n-ally.localesPaths": ["locales"],
"i18n-ally.keystyle": "nested",
"i18n-ally.extract.ignoredByFiles": {
"src\\routes\\__layout.svelte": ["Coolify", "coolLabs logo"]
}
}

View File

@ -4,7 +4,7 @@
"version": "2.2.7", "version": "2.2.7",
"license": "AGPL-3.0", "license": "AGPL-3.0",
"scripts": { "scripts": {
"dev": "docker-compose -f docker-compose-dev.yaml up -d && NODE_ENV=development svelte-kit dev", "dev": "docker-compose -f docker-compose-dev.yaml up -d && cross-env NODE_ENV=development & svelte-kit dev",
"dev:stop": "docker-compose -f docker-compose-dev.yaml down", "dev:stop": "docker-compose -f docker-compose-dev.yaml down",
"dev:logs": "docker-compose -f docker-compose-dev.yaml logs -f --tail 10", "dev:logs": "docker-compose -f docker-compose-dev.yaml logs -f --tail 10",
"studio": "npx prisma studio", "studio": "npx prisma studio",
@ -37,6 +37,7 @@
"@typescript-eslint/parser": "4.31.1", "@typescript-eslint/parser": "4.31.1",
"@zerodevx/svelte-toast": "0.7.1", "@zerodevx/svelte-toast": "0.7.1",
"autoprefixer": "10.4.4", "autoprefixer": "10.4.4",
"cross-env": "^7.0.3",
"cross-var": "1.1.0", "cross-var": "1.1.0",
"eslint": "7.32.0", "eslint": "7.32.0",
"eslint-config-prettier": "8.5.0", "eslint-config-prettier": "8.5.0",
@ -50,6 +51,7 @@
"prisma": "3.11.1", "prisma": "3.11.1",
"svelte": "3.46.4", "svelte": "3.46.4",
"svelte-check": "2.4.6", "svelte-check": "2.4.6",
"svelte-i18n": "^3.3.13",
"svelte-preprocess": "4.10.4", "svelte-preprocess": "4.10.4",
"svelte-select": "^4.4.7", "svelte-select": "^4.4.7",
"tailwindcss": "3.0.23", "tailwindcss": "3.0.23",

102
pnpm-lock.yaml generated
View File

@ -20,6 +20,7 @@ specifiers:
compare-versions: 4.1.3 compare-versions: 4.1.3
cookie: 0.4.2 cookie: 0.4.2
cooltipz-css: ^2.1.0 cooltipz-css: ^2.1.0
cross-env: ^7.0.3
cross-var: 1.1.0 cross-var: 1.1.0
cuid: 2.1.8 cuid: 2.1.8
dayjs: 1.11.0 dayjs: 1.11.0
@ -45,6 +46,7 @@ specifiers:
prisma: 3.11.1 prisma: 3.11.1
svelte: 3.46.4 svelte: 3.46.4
svelte-check: 2.4.6 svelte-check: 2.4.6
svelte-i18n: ^3.3.13
svelte-kit-cookie-session: 2.1.2 svelte-kit-cookie-session: 2.1.2
svelte-preprocess: 4.10.4 svelte-preprocess: 4.10.4
svelte-select: ^4.4.7 svelte-select: ^4.4.7
@ -92,6 +94,7 @@ devDependencies:
'@typescript-eslint/parser': 4.31.1_eslint@7.32.0+typescript@4.6.3 '@typescript-eslint/parser': 4.31.1_eslint@7.32.0+typescript@4.6.3
'@zerodevx/svelte-toast': 0.7.1 '@zerodevx/svelte-toast': 0.7.1
autoprefixer: 10.4.4_postcss@8.4.12 autoprefixer: 10.4.4_postcss@8.4.12
cross-env: 7.0.3
cross-var: 1.1.0 cross-var: 1.1.0
eslint: 7.32.0 eslint: 7.32.0
eslint-config-prettier: 8.5.0_eslint@7.32.0 eslint-config-prettier: 8.5.0_eslint@7.32.0
@ -105,6 +108,7 @@ devDependencies:
prisma: 3.11.1 prisma: 3.11.1
svelte: 3.46.4 svelte: 3.46.4
svelte-check: 2.4.6_postcss@8.4.12+svelte@3.46.4 svelte-check: 2.4.6_postcss@8.4.12+svelte@3.46.4
svelte-i18n: 3.3.13_svelte@3.46.4
svelte-preprocess: 4.10.4_296873641a0ad9f42fe92172d27bcedd svelte-preprocess: 4.10.4_296873641a0ad9f42fe92172d27bcedd
svelte-select: 4.4.7 svelte-select: 4.4.7
tailwindcss: 3.0.23_b89136460714832cdda11d1e9d57d1ff tailwindcss: 3.0.23_b89136460714832cdda11d1e9d57d1ff
@ -180,6 +184,55 @@ packages:
- supports-color - supports-color
dev: true dev: true
/@formatjs/ecma402-abstract/1.11.4:
resolution:
{
integrity: sha512-EBikYFp2JCdIfGEb5G9dyCkTGDmC57KSHhRQOC3aYxoPWVZvfWCDjZwkGYHN7Lis/fmuWl906bnNTJifDQ3sXw==
}
dependencies:
'@formatjs/intl-localematcher': 0.2.25
tslib: 2.3.1
dev: true
/@formatjs/fast-memoize/1.2.1:
resolution:
{
integrity: sha512-Rg0e76nomkz3vF9IPlKeV+Qynok0r7YZjL6syLz4/urSg0IbjPZCB/iYUMNsYA643gh4mgrX3T7KEIFIxJBQeg==
}
dependencies:
tslib: 2.3.1
dev: true
/@formatjs/icu-messageformat-parser/2.0.19:
resolution:
{
integrity: sha512-8HsLm9YLyVVIDMyBJb7wmve2wGd461cUwJ470eUog5YH5ZsF4p5lgvaJ+oGKxz1mrSMNNdDHU9v/NDsS+z+ilg==
}
dependencies:
'@formatjs/ecma402-abstract': 1.11.4
'@formatjs/icu-skeleton-parser': 1.3.6
tslib: 2.3.1
dev: true
/@formatjs/icu-skeleton-parser/1.3.6:
resolution:
{
integrity: sha512-I96mOxvml/YLrwU2Txnd4klA7V8fRhb6JG/4hm3VMNmeJo1F03IpV2L3wWt7EweqNLES59SZ4d6hVOPCSf80Bg==
}
dependencies:
'@formatjs/ecma402-abstract': 1.11.4
tslib: 2.3.1
dev: true
/@formatjs/intl-localematcher/0.2.25:
resolution:
{
integrity: sha512-YmLcX70BxoSopLFdLr1Ds99NdlTI2oWoLbaUW2M406lxOIPzE1KQhRz2fPUkq34xVZQaihCoU29h0KK7An3bhA==
}
dependencies:
tslib: 2.3.1
dev: true
/@humanwhocodes/config-array/0.5.0: /@humanwhocodes/config-array/0.5.0:
resolution: resolution:
{ {
@ -2081,6 +2134,17 @@ packages:
luxon: 1.28.0 luxon: 1.28.0
dev: false dev: false
/cross-env/7.0.3:
resolution:
{
integrity: sha512-+/HKd6EgcQCJGh2PSjZuUitQBQynKor4wrFbRg4DtAgS1aWO+gU52xpH7M9ScGgXSYmAVS9bIJ8EzuaGw0oNAw==
}
engines: { node: '>=10.14', npm: '>=6', yarn: '>=1' }
hasBin: true
dependencies:
cross-spawn: 7.0.3
dev: true
/cross-spawn/5.1.0: /cross-spawn/5.1.0:
resolution: { integrity: sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk= } resolution: { integrity: sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk= }
dependencies: dependencies:
@ -2190,6 +2254,14 @@ packages:
} }
dev: true dev: true
/deepmerge/4.2.2:
resolution:
{
integrity: sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg==
}
engines: { node: '>=0.10.0' }
dev: true
/defer-to-connect/2.0.1: /defer-to-connect/2.0.1:
resolution: resolution:
{ {
@ -3390,6 +3462,18 @@ packages:
integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ== integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==
} }
/intl-messageformat/9.12.0:
resolution:
{
integrity: sha512-5Q9j21JreB1G27/CqMYsA+pvJ19JjHyhiTSeUuvZK9BCDJGHtOLgpUUcGM+GLHiUuoVMKVeeX1smamiVHQrSKQ==
}
dependencies:
'@formatjs/ecma402-abstract': 1.11.4
'@formatjs/fast-memoize': 1.2.1
'@formatjs/icu-messageformat-parser': 2.0.19
tslib: 2.3.1
dev: true
/invariant/2.2.4: /invariant/2.2.4:
resolution: resolution:
{ {
@ -5159,6 +5243,24 @@ packages:
svelte: 3.46.4 svelte: 3.46.4
dev: true dev: true
/svelte-i18n/3.3.13_svelte@3.46.4:
resolution:
{
integrity: sha512-RQM+ys4+Y9ztH//tX22H1UL2cniLNmIR+N4xmYygV6QpQ6EyQvloZiENRew8XrVzfvJ8HaE8NU6/yurLkl7z3g==
}
engines: { node: '>= 11.15.0' }
hasBin: true
peerDependencies:
svelte: ^3.25.1
dependencies:
deepmerge: 4.2.2
estree-walker: 2.0.2
intl-messageformat: 9.12.0
sade: 1.7.4
svelte: 3.46.4
tiny-glob: 0.2.9
dev: true
/svelte-kit-cookie-session/2.1.2: /svelte-kit-cookie-session/2.1.2:
resolution: resolution:
{ {

View File

@ -12,6 +12,7 @@
</script> </script>
<script> <script>
import { _ } from 'svelte-i18n';
export let status; export let status;
export let error; export let error;
</script> </script>
@ -20,7 +21,8 @@
<div class="pb-10 text-7xl font-bold">{status}</div> <div class="pb-10 text-7xl font-bold">{status}</div>
<div class="text-3xl font-bold">Ooops you are lost! But don't be afraid!</div> <div class="text-3xl font-bold">Ooops you are lost! But don't be afraid!</div>
<div class="text-xl"> <div class="text-xl">
You can find your way back <a href="/" class="font-bold uppercase text-sky-400">here</a> {$_('error.you_can_find_your_way_back')}
<a href="/" class="font-bold uppercase text-sky-400">{$_('error.here')}</a>
</div> </div>
<div class="py-10 text-xs font-bold"> <div class="py-10 text-xs font-bold">
<pre <pre

View File

@ -38,7 +38,18 @@
import { errorNotification } from '$lib/form'; import { errorNotification } from '$lib/form';
import { asyncSleep } from '$lib/components/common'; import { asyncSleep } from '$lib/components/common';
import { del, get, post } from '$lib/api'; import { del, get, post } from '$lib/api';
import { browser, dev } from '$app/env'; import { register, init, _, getLocaleFromNavigator } from 'svelte-i18n';
async function setup() {
register('en', () => import('../../static/locales/en.json'));
return await Promise.allSettled([
// TODO: add some more stuff you want to init ...
init({ initialLocale: getLocaleFromNavigator(), fallbackLocale: 'en' })
]);
}
const setupResult = setup();
let isUpdateAvailable = false; let isUpdateAvailable = false;
@ -104,7 +115,7 @@
return window.location.reload(); return window.location.reload();
} else { } else {
await post(`/update.json`, { type: 'update', latestVersion }); await post(`/update.json`, { type: 'update', latestVersion });
toast.push('Update completed.<br><br>Waiting for the new version to start...'); toast.push(`${$_('layout.update_done')}<br><br>${$_('layout.wait_new_version_startup')}`);
let reachable = false; let reachable = false;
let tries = 0; let tries = 0;
do { do {
@ -118,7 +129,7 @@
if (reachable) break; if (reachable) break;
tries++; tries++;
} while (!reachable || tries < 120); } while (!reachable || tries < 120);
toast.push('New version reachable. Reloading...'); toast.push($_('layout.new_version'));
updateStatus.loading = false; updateStatus.loading = false;
updateStatus.success = true; updateStatus.success = true;
await asyncSleep(3000); await asyncSleep(3000);
@ -135,6 +146,10 @@
<svelte:head> <svelte:head>
<title>Coolify</title> <title>Coolify</title>
</svelte:head> </svelte:head>
{#await setupResult}
Please wait...
{:then}
<SvelteToast options={{ intro: { y: -64 }, duration: 3000, pausable: true }} /> <SvelteToast options={{ intro: { y: -64 }, duration: 3000, pausable: true }} />
{#if $session.userId} {#if $session.userId}
<nav class="nav-main"> <nav class="nav-main">
@ -321,7 +336,7 @@
{#if isUpdateAvailable} {#if isUpdateAvailable}
<button <button
disabled={updateStatus.success === false} disabled={updateStatus.success === false}
title="Update available" title={$_('layout.update_available')}
on:click={update} on:click={update}
class="icons tooltip-right bg-gradient-to-r from-purple-500 via-pink-500 to-red-500 text-white duration-75 hover:scale-105" class="icons tooltip-right bg-gradient-to-r from-purple-500 via-pink-500 to-red-500 text-white duration-75 hover:scale-105"
> >
@ -519,7 +534,7 @@
bind:value={selectedTeamId} bind:value={selectedTeamId}
on:change={switchTeam} on:change={switchTeam}
> >
<option value="" disabled selected>Switch to a different team...</option> <option value="" disabled selected>{$_('layout.switch_to_a_different_team')}</option>
{#each teams as team} {#each teams as team}
<option value={team.teamId}>{team.team.name} - {team.permission}</option> <option value={team.teamId}>{team.team.name} - {team.permission}</option>
{/each} {/each}
@ -528,3 +543,6 @@
<main> <main>
<slot /> <slot />
</main> </main>
{:catch error}
<p style="color: red">{error.message}</p>
{/await}

13
static/locales/en.json Normal file
View File

@ -0,0 +1,13 @@
{
"layout": {
"update_done": "Update completed.",
"wait_new_version_startup": "Waiting for the new version to start...",
"new_version": "New version reachable. Reloading...",
"switch_to_a_different_team": "Switch to a different team...",
"update_available": "Update available"
},
"error": {
"you_can_find_your_way_back": "You can find your way back",
"here": "here"
}
}

View File

@ -12,6 +12,12 @@ const config = {
vite: { vite: {
optimizeDeps: { optimizeDeps: {
exclude: ['svelte-kit-cookie-session'] exclude: ['svelte-kit-cookie-session']
},
server: {
fs: {
// Allow serving files from one level up to the project root
allow: ['../locales']
}
} }
} }
} }