Prevent style removal of client:only components (#8472)
This commit is contained in:
parent
1ed21d10db
commit
fa77fa63d9
5 changed files with 60 additions and 0 deletions
5
.changeset/grumpy-hotels-heal.md
Normal file
5
.changeset/grumpy-hotels-heal.md
Normal file
|
@ -0,0 +1,5 @@
|
||||||
|
---
|
||||||
|
'astro': patch
|
||||||
|
---
|
||||||
|
|
||||||
|
Prevent client:only styles from being removed in dev (View Transitions)
|
|
@ -113,6 +113,11 @@ const { fallback = 'animate' } = Astro.props as Props;
|
||||||
|
|
||||||
const parser = new DOMParser();
|
const parser = new DOMParser();
|
||||||
|
|
||||||
|
// A noop element used to prevent styles from being removed
|
||||||
|
if(import.meta.env.DEV) {
|
||||||
|
var noopEl: string | undefined = document.createElement('div');
|
||||||
|
}
|
||||||
|
|
||||||
async function updateDOM(doc: Document, loc: URL, state?: State, fallback?: Fallback) {
|
async function updateDOM(doc: Document, loc: URL, state?: State, fallback?: Fallback) {
|
||||||
// Check for a head element that should persist, either because it has the data
|
// Check for a head element that should persist, either because it has the data
|
||||||
// attribute or is a link el.
|
// attribute or is a link el.
|
||||||
|
@ -139,6 +144,16 @@ const { fallback = 'animate' } = Astro.props as Props;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// Only run this in dev. This will get stripped from production builds and is not needed.
|
||||||
|
if(import.meta.env.DEV) {
|
||||||
|
if(el.tagName === 'STYLE' && el.dataset.viteDevId) {
|
||||||
|
const devId = el.dataset.viteDevId;
|
||||||
|
// If this same style tag exists, remove it from the new page
|
||||||
|
return doc.querySelector(`style[data-astro-dev-id="${devId}"]`)
|
||||||
|
// Otherwise, keep it anyways. This is client:only styles.
|
||||||
|
|| noopEl;
|
||||||
|
}
|
||||||
|
}
|
||||||
return null;
|
return null;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,10 @@
|
||||||
|
---
|
||||||
|
import Layout from '../components/Layout.astro';
|
||||||
|
import Island from '../components/Island';
|
||||||
|
---
|
||||||
|
<Layout>
|
||||||
|
<a id="click-two" href="/client-only-two">go to page 2</a>
|
||||||
|
<div transition:persist="island">
|
||||||
|
<Island client:only count={5}>message here</Island>
|
||||||
|
</div>
|
||||||
|
</Layout>
|
|
@ -0,0 +1,10 @@
|
||||||
|
---
|
||||||
|
import Layout from '../components/Layout.astro';
|
||||||
|
import Island from '../components/Island';
|
||||||
|
---
|
||||||
|
<Layout>
|
||||||
|
<p id="page-two">Page 2</p>
|
||||||
|
<div transition:persist="island">
|
||||||
|
<Island client:only count={5}>message here</Island>
|
||||||
|
</div>
|
||||||
|
</Layout>
|
|
@ -565,4 +565,24 @@ test.describe('View Transitions', () => {
|
||||||
p = page.locator('#one');
|
p = page.locator('#one');
|
||||||
await expect(p, 'should have content').toHaveText('Page 1');
|
await expect(p, 'should have content').toHaveText('Page 1');
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test("client:only styles are retained on transition", async ({ page, astro }) => {
|
||||||
|
const totalExpectedStyles = 8;
|
||||||
|
|
||||||
|
// Go to page 1
|
||||||
|
await page.goto(astro.resolveUrl('/client-only-one'));
|
||||||
|
let msg = page.locator('.counter-message');
|
||||||
|
await expect(msg).toHaveText('message here');
|
||||||
|
|
||||||
|
let styles = await page.locator('style').all();
|
||||||
|
expect(styles.length).toEqual(totalExpectedStyles);
|
||||||
|
|
||||||
|
await page.click('#click-two');
|
||||||
|
|
||||||
|
let pageTwo = page.locator('#page-two');
|
||||||
|
await expect(pageTwo, 'should have content').toHaveText('Page 2');
|
||||||
|
|
||||||
|
styles = await page.locator('style').all();
|
||||||
|
expect(styles.length).toEqual(totalExpectedStyles, 'style count has not changed');
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
Loading…
Reference in a new issue