npx sv migrate app-state only migrates some files
A simple, string-based migration for sveltejs/kit#13140 (tested on that repo, zero false-positives, less than five false negatives)
We can switch to using the Svelte parser if people prefer that to get a bit better with regards to only actually transforming identifiers, but to me this seems to work fine.
Fixes #485
This is the simplest approach I could think of--I know it can get a little hairy with all the versions of Svelte and SvelteKit out there. Still, I believe most of the logic is already in place with the CLI to make sure the user has the right versioning heading into the migration.
This only runs the app-state migration script if the user has SvelteKit. It doesn't really log anything or add any error handling--I'll leave those up to you if desired.
Also, I know you guys have a contributing guide on the docket, but I was wondering how exactly you test this CLI on your own projects. I ask because I ended up using npm link which is pretty standard, but I had to edit these lines of code to make sure that when I tested my fixes locally that it linked to my scripts instead of pulling @latest from npx 🙏
Run it in the web directory of https://github.com/immich-app/immich and it won't migrate anything. Some stuff was already migrated in immich-app/immich#14807, but it only got 9 out of 22 occurrences of $app/stores
Here is a failing test (note the word page in an unrelated import). I tried fixing the bug but failed.
test('Updates $app/store #4', () => {
const result = transform_svelte_code(
`<script>
import { page } from '$app/stores';
import Comp from '$lib/page/Comp.svelte'
</script>
<div>{$page.url}</div>
<button onclick={() => {
console.log($page.state);
}}></button>
`
);
assert.equal(
result,
`<script>
import { page } from '$app/state';
import Comp from '$lib/page/Comp.svelte'
</script>
<div>{page.url}</div>
<button onclick={() => {
console.log(page.state);
}}></button>
`
);
});
FYI @dummdidumm
I think it fails due to this line: https://github.com/sveltejs/cli/blob/e325bb2c71fe3fefce4cfcb07e3ab33870eddb45/packages/migrate/migrations/app-state/migrate.js#L70
Here we return early and skip the migration if the imported store alias is not prefixed with a $, unless a few conditions are met. We probably need to add another condition here (while checking for false positives) to check if the alias is part of a string or a comment.
For e.g., if a component has the following line, it won't be migrated according to the current logic:
const str = "before page after";
or
// this is a pageOne thing I noticed when working on #494 was that if I ran the migration on a newly created project it would work great. However, when I changed an $app/state back to $app/stores after the initial migration, subsequent runs wouldn't fix it.
I don't know if that helps pinpoint any issues here or just muddies the waters.
That's because the word page will appear already, and that messes with the script somehow. This is basically also the testcase i mentioned above.