-
Notifications
You must be signed in to change notification settings - Fork 25.3k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
JavaScript with Blazor static server rendering #30922
Conversation
aspnetcore/blazor/javascript-interoperability/static-server-rendering.md
Outdated
Show resolved
Hide resolved
aspnetcore/blazor/javascript-interoperability/static-server-rendering.md
Outdated
Show resolved
Hide resolved
Here's a new version of const pageScriptInfoBySrc = new Map();
function registerPageScriptElement(src) {
if (!src) {
throw new Error('Must provide a non-empty value for the "src" attribute.');
}
let pageScriptInfo = pageScriptInfoBySrc.get(src);
if (pageScriptInfo) {
pageScriptInfo.referenceCount++;
} else {
pageScriptInfo = { referenceCount: 1, module: null };
pageScriptInfoBySrc.set(src, pageScriptInfo);
initializePageScriptModule(src, pageScriptInfo);
}
}
function unregisterPageScriptElement(src) {
if (!src) {
return;
}
const pageScriptInfo = pageScriptInfoBySrc.get(src);
if (!pageScriptInfo) {
return;
}
pageScriptInfo.referenceCount--;
}
async function initializePageScriptModule(src, pageScriptInfo) {
// If the path is relative, normalize it by by making it an absolute URL
// with document's the base HREF.
if (src.startsWith("./")) {
src = new URL(src.substr(2), document.baseURI).toString();
}
const module = await import(src);
if (pageScriptInfo.referenceCount <= 0) {
// All page-script elements with the same 'src' were
// unregistered while we were loading the module.
return;
}
pageScriptInfo.module = module;
module.onLoad?.();
module.onUpdate?.();
}
function onEnhancedLoad() {
// Start by invoking 'onDispose' on any modules that are no longer referenced.
for (const [src, { module, referenceCount }] of pageScriptInfoBySrc) {
if (referenceCount <= 0) {
module?.onDispose?.();
pageScriptInfoBySrc.delete(src);
}
}
// Then invoke 'onUpdate' on the remaining modules.
for (const { module } of pageScriptInfoBySrc.values()) {
module?.onUpdate?.();
}
}
export function afterWebStarted(blazor) {
customElements.define('page-script', class extends HTMLElement {
static observedAttributes = ['src'];
// We use attributeChangedCallback instead of connectedCallback
// because a page-script element might get reused between enhanced
// navigations.
attributeChangedCallback(name, oldValue, newValue) {
if (name !== 'src') {
return;
}
this.src = newValue;
unregisterPageScriptElement(oldValue);
registerPageScriptElement(newValue);
}
disconnectedCallback() {
unregisterPageScriptElement(this.src);
}
});
blazor.addEventListener('enhancedload', onEnhancedLoad);
} |
@guardrex If we think this sample is too large to put in the docs, I could post it somewhere else and we could link to it. |
No ... it's fine. Give me a few minutes, and I'll have the commit up for a look 👀. |
Note that I always need to move code comments into the text to get them localized. If they stay in the code, they remain stuck in English forever. Just wanted to let you know why you always see me do that. |
Ok ... I'm done with little nits. |
aspnetcore/blazor/javascript-interoperability/static-server-rendering.md
Outdated
Show resolved
Hide resolved
aspnetcore/blazor/javascript-interoperability/static-server-rendering.md
Outdated
Show resolved
Hide resolved
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks great to me after the pending feedback is addressed 🙂
I see now that this won't work for general calls because the JS object reference is required for JS interop calls. DUH! 🙈😄 I merely detected a difference without thinking it through last night. I'll cross-link this as an example in the JS initializers section. We have a few other cross-linked use cases there. Also, I have an update on the next commit for "static server rendering" (lowercase "s" in "server"), which I think is what DR wants. I still don't know yet if he wants "interactive server rendering" (because "server" only means 'on the server') or "interactive Server rendering" (because "Server" refers to the 'Blazor Server' hosting model ... we're still rather unclear on its role in a BWA ... if it actually is running under a BWA or not for the server-side scenarios). If it refers to 'Blazor Server,' it should be capitalized ... and also because it pairs with "interactive WebAssembly rendering," which is capitalized because "WebAssembly" is a proper noun. |
I'm going to hold here for a sec so that you can confirm if the updates on the last couple of commits are correct. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM!
Fixes #30921
Addresses #28161
Mackinnon ... Check everything because I made a few guesses along the way ... and we know how that goes 🦖🙈😆.
Internal previews