Skip to content

Commit

Permalink
internal: Example of using incremental rehydration
Browse files Browse the repository at this point in the history
This PR adds an example showing how to use intersection observer in
conjunction with partial rehydration.
  • Loading branch information
chadhietala committed Nov 16, 2020
1 parent 5c278b2 commit 32c044d
Show file tree
Hide file tree
Showing 6 changed files with 49 additions and 66 deletions.
64 changes: 31 additions & 33 deletions packages/example-apps/partial-rehydration/index.ts
Original file line number Diff line number Diff line change
@@ -1,38 +1,36 @@
import { renderComponent } from '@glimmer/core';
import RehydratableRegion from './src/RehydratableRegion';
import RehydratableCounter from './src/RehydratableCounter';

document.addEventListener(
'DOMContentLoaded',
() => {
const observer = new IntersectionObserver(
(entries) => {
entries.forEach(async (entry) => {
if (entry.isIntersecting) {
await renderComponent(RehydratableRegion, {
element: document.querySelector('.static-component'),
args: {},
rehydrate: true,
});
}
});
},
{
root: null,
}
);

const rehydratables = Array.from(document.querySelectorAll('[data-hydrate]'));
rehydrate({
get RehydratableCounter() {
// Can load components async
return Promise.resolve(RehydratableCounter);
},
});

console.log(rehydratables);
for (const el of rehydratables) {
observer.observe(el);
function rehydrate(componentMapping) {
const hasHydrated = new WeakSet();
const observer = new IntersectionObserver(
(entries) => {
entries.forEach(async (entry) => {
if (entry.isIntersecting && !hasHydrated.has(entry.target)) {
await renderComponent(await componentMapping[entry.target.dataset.hydrate], {
element: entry.target.parentElement,
args: JSON.parse(entry.target.querySelector('script').textContent),
rehydrate: true,
});
hasHydrated.add(entry.target);
}
});
},
{
root: null,
}
);

// const element = document.querySelector('.static-component');
// renderComponent(RehydratingComponent, {
// element: element!,
// rehydrate: true,
// });
},
{ once: true }
);
const rehydratables = Array.from(document.querySelectorAll('[data-hydrate]'));
console.log(rehydratables);
for (const el of rehydratables) {
observer.observe(el);
}
}
3 changes: 2 additions & 1 deletion packages/example-apps/partial-rehydration/server.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ export default async function handler(
clientsideBundleLocation: string
): Promise<void> {
const ssrOutput = await renderToString(StaticComponent, {
args: { foo: { bar: 'bar' } },
rehydrate: true,
});

Expand All @@ -22,7 +23,7 @@ export default async function handler(
</head>
<body>
<div id="app">${ssrOutput}</div>
<script src="${clientsideBundleLocation}"></script>
<script async src="${clientsideBundleLocation}"></script>
</body>
</html>
`);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,13 +15,12 @@ class RehydratableCounter extends Component {
setComponentTemplate(
createTemplate(
{ on, RehydratableRegion },
`<div>
<RehydratableRegion @data={{this.args}} as |data|>
<h1>{{data.message}}</h1>
`<RehydratableRegion @name="RehydratableCounter" @data={{this.args}}>
<h1>{{@message}}</h1>
<p>{{@foo.bar}}</p>
<p>You have clicked the button {{this.count}} times.</p>
<button {{on "click" this.increment}}>Click</button>
<button {{on "click" this.increment}}>Click</button>
</RehydratableRegion>
</div>
`
),
RehydratableCounter
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,9 @@ function toJSON(args) {
export default setComponentTemplate(
createTemplate(
{ toJSON },
`<div data-hydrate="" ...attributes>
`<div data-hydrate="{{@name}}" ...attributes>
<script type="application/hydrate">{{toJSON @data}}</script>
{{yield @data}}
{{yield}}
</div>
`
),
Expand Down

This file was deleted.

11 changes: 10 additions & 1 deletion packages/example-apps/partial-rehydration/src/StaticComponent.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,16 @@ const StaticComponent = setComponentTemplate(
{ RehydratableCounter },
`<div class="static-component">
<h1>Hello I am a static component. I don't change after page load.</h1>
<RehydratableCounter @message="Hello World" />
<RehydratableCounter @message="Hello World" @foo={{@foo}} />
<RehydratableCounter @message="Bye" />
<RehydratableCounter @message="Ciao" />
<RehydratableCounter @message="Adios" />
<RehydratableCounter @message="Hey1" />
<RehydratableCounter @message="Hey2" />
<RehydratableCounter @message="Hey3" />
<RehydratableCounter @message="Hey4" />
<RehydratableCounter @message="Hey5" />
<RehydratableCounter @message="Hey6" />
</div>
`
),
Expand Down

0 comments on commit 32c044d

Please sign in to comment.