feat: complete Svelte 5 migration across entire application
All checks were successful
CI / update (push) Successful in 2m8s
All checks were successful
CI / update (push) Successful in 2m8s
Migrated all components and routes from Svelte 4 to Svelte 5 syntax:
- Converted export let → $props() with generic type syntax
- Replaced createEventDispatcher → callback props
- Migrated $: reactive statements → $derived() and $effect()
- Updated two-way bindings with $bindable()
- Fixed TypeScript syntax: added lang="ts" to script tags
- Converted inline type annotations to generic parameter syntax
- Updated deprecated event directives to Svelte 5 syntax:
- on:click → onclick
- on:submit → onsubmit
- on:change → onchange
- Converted deprecated <slot> elements → {@render children()}
- Updated slot props to Snippet types
- Fixed season/icon selector components with {#snippet} blocks
- Fixed non-reactive state by converting let → $state()
- Fixed infinite loop in EnhancedBalance by converting $effect → $derived
- Fixed Chart.js integration by converting $state proxies to plain arrays
- Updated cospend dashboard and payment pages with proper reactivity
- Migrated 20+ route files from export let data → $props()
- Fixed TypeScript type annotations in page components
- Updated reactive statements in error and cospend routes
- Removed invalid onchange attribute from Toggle component
- Fixed modal ID isolation in CreateIngredientList/CreateStepList
- Fixed dark mode button visibility in TranslationApproval
- Build now succeeds with zero deprecation warnings
All functionality tested and working. No breaking changes to user experience.
This commit is contained in:
@@ -5,7 +5,7 @@
|
||||
import Card from '$lib/components/Card.svelte';
|
||||
import Search from '$lib/components/Search.svelte';
|
||||
import LazyCategory from '$lib/components/LazyCategory.svelte';
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
let current_month = new Date().getMonth() + 1;
|
||||
|
||||
// Search state
|
||||
|
||||
@@ -16,7 +16,7 @@
|
||||
import { onDestroy } from 'svelte';
|
||||
import { recipeTranslationStore } from '$lib/stores/recipeTranslation';
|
||||
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
|
||||
// Set store for recipe translation data so UserHeader can access it
|
||||
// Use $effect instead of onMount to react to data changes during client-side navigation
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
import type { PageData } from './$types';
|
||||
import '$lib/css/nordtheme.css';
|
||||
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
|
||||
const isEnglish = data.lang === 'en';
|
||||
const pageTitle = isEnglish ? 'Administration' : 'Administration';
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<script lang="ts">
|
||||
import type { PageData } from './$types';
|
||||
import "$lib/css/nordtheme.css";
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
import TagCloud from '$lib/components/TagCloud.svelte';
|
||||
import TagBall from '$lib/components/TagBall.svelte';
|
||||
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
import type { PageData } from './$types';
|
||||
import Recipes from '$lib/components/Recipes.svelte';
|
||||
import Search from '$lib/components/Search.svelte';
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
let current_month = new Date().getMonth() + 1;
|
||||
import Card from '$lib/components/Card.svelte'
|
||||
import { rand_array } from '$lib/js/randomize';
|
||||
|
||||
@@ -16,7 +16,7 @@
|
||||
import { portions } from '$lib/js/portions_store';
|
||||
import { img } from '$lib/js/img_store';
|
||||
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
|
||||
let preamble = $state(data.recipe.preamble);
|
||||
let addendum = $state(data.recipe.addendum);
|
||||
@@ -612,8 +612,8 @@ button.action_button{
|
||||
|
||||
{#if !showTranslationWorkflow}
|
||||
<div class=submit_buttons>
|
||||
<button class=action_button on:click={doDelete}><p>Löschen</p><Cross fill=white width=2rem height=2rem></Cross></button>
|
||||
<button class=action_button on:click={prepareSubmit}><p>Weiter zur Übersetzung</p><Check fill=white width=2rem height=2rem></Check></button>
|
||||
<button class=action_button onclick={doDelete}><p>Löschen</p><Cross fill=white width=2rem height=2rem></Cross></button>
|
||||
<button class=action_button onclick={prepareSubmit}><p>Weiter zur Übersetzung</p><Check fill=white width=2rem height=2rem></Check></button>
|
||||
</div>
|
||||
{/if}
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
import Recipes from '$lib/components/Recipes.svelte';
|
||||
import Card from '$lib/components/Card.svelte';
|
||||
import Search from '$lib/components/Search.svelte';
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
let current_month = new Date().getMonth() + 1;
|
||||
|
||||
const isEnglish = $derived(data.lang === 'en');
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
import SeasonLayout from '$lib/components/SeasonLayout.svelte'
|
||||
import Card from '$lib/components/Card.svelte';
|
||||
import Search from '$lib/components/Search.svelte';
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
</script>
|
||||
<style>
|
||||
a{
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
import MediaScroller from '$lib/components/MediaScroller.svelte';
|
||||
import Card from '$lib/components/Card.svelte';
|
||||
import Search from '$lib/components/Search.svelte';
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
import { rand_array } from '$lib/js/randomize';
|
||||
|
||||
// Search state
|
||||
@@ -27,9 +27,11 @@
|
||||
});
|
||||
</script>
|
||||
<IconLayout icons={data.icons} active_icon={data.icon} routePrefix="/{data.recipeLang}" lang={data.lang} recipes={data.season} onSearchResults={handleSearchResults}>
|
||||
<Recipes slot=recipes>
|
||||
{#each rand_array(filteredRecipes) as recipe}
|
||||
<Card {recipe} icon_override=true isFavorite={recipe.isFavorite} showFavoriteIndicator={!!data.session?.user} routePrefix="/{data.recipeLang}"></Card>
|
||||
{/each}
|
||||
</Recipes>
|
||||
{#snippet recipesSlot()}
|
||||
<Recipes>
|
||||
{#each rand_array(filteredRecipes) as recipe}
|
||||
<Card {recipe} icon_override=true isFavorite={recipe.isFavorite} showFavoriteIndicator={!!data.session?.user} routePrefix="/{data.recipeLang}"></Card>
|
||||
{/each}
|
||||
</Recipes>
|
||||
{/snippet}
|
||||
</IconLayout>
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
import Recipes from '$lib/components/Recipes.svelte';
|
||||
import Search from '$lib/components/Search.svelte';
|
||||
import Card from '$lib/components/Card.svelte';
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
let current_month = new Date().getMonth() + 1;
|
||||
|
||||
const isEnglish = $derived(data.lang === 'en');
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
import SeasonLayout from '$lib/components/SeasonLayout.svelte'
|
||||
import Card from '$lib/components/Card.svelte';
|
||||
import Search from '$lib/components/Search.svelte';
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
let current_month = new Date().getMonth() + 1
|
||||
import { rand_array } from '$lib/js/randomize';
|
||||
|
||||
@@ -35,9 +35,11 @@
|
||||
</script>
|
||||
|
||||
<SeasonLayout active_index={current_month-1} {months} routePrefix="/{data.recipeLang}" lang={data.lang} recipes={data.season} onSearchResults={handleSearchResults}>
|
||||
<Recipes slot=recipes>
|
||||
{#each rand_array(filteredRecipes) as recipe}
|
||||
<Card {recipe} {current_month} isFavorite={recipe.isFavorite} showFavoriteIndicator={!!data.session?.user} routePrefix="/{data.recipeLang}"></Card>
|
||||
{/each}
|
||||
</Recipes>
|
||||
{#snippet recipesSlot()}
|
||||
<Recipes>
|
||||
{#each rand_array(filteredRecipes) as recipe}
|
||||
<Card {recipe} {current_month} isFavorite={recipe.isFavorite} showFavoriteIndicator={!!data.session?.user} routePrefix="/{data.recipeLang}"></Card>
|
||||
{/each}
|
||||
</Recipes>
|
||||
{/snippet}
|
||||
</SeasonLayout>
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
import MediaScroller from '$lib/components/MediaScroller.svelte';
|
||||
import Card from '$lib/components/Card.svelte';
|
||||
import Search from '$lib/components/Search.svelte';
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
|
||||
const isEnglish = $derived(data.lang === 'en');
|
||||
const months = $derived(isEnglish
|
||||
@@ -33,9 +33,11 @@
|
||||
});
|
||||
</script>
|
||||
<SeasonLayout active_index={data.month -1} {months} routePrefix="/{data.recipeLang}" lang={data.lang} recipes={data.season} onSearchResults={handleSearchResults}>
|
||||
<Recipes slot=recipes>
|
||||
{#each rand_array(filteredRecipes) as recipe}
|
||||
<Card {recipe} icon_override=true isFavorite={recipe.isFavorite} showFavoriteIndicator={!!data.session?.user} routePrefix="/{data.recipeLang}"></Card>
|
||||
{/each}
|
||||
</Recipes>
|
||||
{#snippet recipesSlot()}
|
||||
<Recipes>
|
||||
{#each rand_array(filteredRecipes) as recipe}
|
||||
<Card {recipe} icon_override=true isFavorite={recipe.isFavorite} showFavoriteIndicator={!!data.session?.user} routePrefix="/{data.recipeLang}"></Card>
|
||||
{/each}
|
||||
</Recipes>
|
||||
{/snippet}
|
||||
</SeasonLayout>
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<script lang="ts">
|
||||
import type { PageData } from './$types';
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
import "$lib/css/nordtheme.css";
|
||||
import TagCloud from '$lib/components/TagCloud.svelte';
|
||||
import TagBall from '$lib/components/TagBall.svelte';
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<script lang="ts">
|
||||
import type { PageData } from './$types';
|
||||
import Recipes from '$lib/components/Recipes.svelte';
|
||||
let { data }: { data: PageData } = $props();
|
||||
let { data } = $props<{ data: PageData }>();
|
||||
let current_month = new Date().getMonth() + 1;
|
||||
import Card from '$lib/components/Card.svelte'
|
||||
import Search from '$lib/components/Search.svelte';
|
||||
|
||||
Reference in New Issue
Block a user