Skip to content

Commit 16b2e69

Browse files
committed
replace loading with _loading to avoid variable conflicts and restructure resource handling logic
1 parent 0af2c2b commit 16b2e69

File tree

3 files changed

+42
-18
lines changed

3 files changed

+42
-18
lines changed

.changeset/happy-sites-count.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
---
2+
"solid-js": patch
3+
---
4+
5+
- Handle promise resolution in `createResource` with improved inspection and serialization logic
6+
- Fixed the issue with promise return value in Synchronous Functions in SSR.

.changeset/moody-clowns-vanish.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
"solid-js": patch
3+
---
4+
5+
rename `loading` to `_loading`, refactor resource preparation logic and simplify promise handling

packages/solid/src/server/rendering.ts

Lines changed: 31 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -367,13 +367,13 @@ export function ErrorBoundary(props: {
367367
export interface Resource<T> {
368368
(): T | undefined;
369369
state: "unresolved" | "pending" | "ready" | "refreshing" | "errored";
370-
loading: boolean;
370+
_loading: boolean;
371371
error: any;
372372
latest: T | undefined;
373373
}
374374

375375
type SuspenseContextType = {
376-
resources: Map<string, { loading: boolean; error: any }>;
376+
resources: Map<string, { _loading: boolean; error: any }>;
377377
completed: () => void;
378378
};
379379

@@ -435,7 +435,6 @@ export function createResource<T, S>(
435435
fetcher = source as ResourceFetcher<S, T>;
436436
source = true as ResourceSource<S>;
437437
}
438-
439438
const contexts = new Set<SuspenseContextType>();
440439
const id = sharedConfig.getNextContextId();
441440
let resource: { ref?: any; data?: T } = {};
@@ -450,34 +449,48 @@ export function createResource<T, S>(
450449
return resource.ref;
451450
}
452451
}
453-
const read = () => {
452+
const prepareResource = () => {
454453
if (error) throw error;
455454
const resolved =
456455
options.ssrLoadFrom !== "initial" &&
457456
sharedConfig.context!.async &&
458457
"data" in sharedConfig.context!.resources[id];
459458
if (!resolved && resourceContext) resourceContext.push(id);
460-
if (!resolved && read.loading) {
459+
if (!resolved && read._loading) {
461460
const ctx = useContext(SuspenseContext);
462461
if (ctx) {
463462
ctx.resources.set(id, read);
464463
contexts.add(ctx);
465464
}
466465
}
467-
return resolved ? sharedConfig.context!.resources[id].data : value;
466+
return resolved;
467+
};
468+
const read = () => {
469+
return prepareResource() ? sharedConfig.context!.resources[id].data : value;
468470
};
469-
read.loading = false;
471+
const loading = () => {
472+
prepareResource();
473+
return read._loading;
474+
};
475+
read._loading = false;
470476
read.error = undefined as any;
471477
read.state = "initialValue" in options ? "ready" : "unresolved";
472-
Object.defineProperty(read, "latest", {
473-
get() {
474-
return read();
478+
Object.defineProperties(read, {
479+
latest: {
480+
get() {
481+
return read();
482+
}
483+
},
484+
loading: {
485+
get() {
486+
return loading();
487+
}
475488
}
476489
});
477490
function load() {
478491
const ctx = sharedConfig.context!;
479492
if (!ctx.async)
480-
return (read.loading = !!(typeof source === "function" ? (source as () => S)() : source));
493+
return (read._loading = !!(typeof source === "function" ? (source as () => S)() : source));
481494
if (ctx.resources && id in ctx.resources && "data" in ctx.resources[id]) {
482495
value = ctx.resources[id].data;
483496
return;
@@ -495,19 +508,19 @@ export function createResource<T, S>(
495508
p = (fetcher as ResourceFetcher<S, T>)(lookup, { value });
496509
}
497510
if (p != undefined && typeof p === "object" && "then" in p) {
498-
read.loading = true;
511+
read._loading = true;
499512
read.state = "pending";
500513
p = p
501514
.then(res => {
502-
read.loading = false;
515+
read._loading = false;
503516
read.state = "ready";
504517
ctx.resources[id].data = res;
505518
p = null;
506519
notifySuspense(contexts);
507520
return res;
508521
})
509522
.catch(err => {
510-
read.loading = false;
523+
read._loading = false;
511524
read.state = "errored";
512525
read.error = error = castError(err);
513526
p = null;
@@ -550,15 +563,15 @@ export function lazy<T extends Component<any>>(
550563
else load(id);
551564
if (p.resolved) return p.resolved(props);
552565
const ctx = useContext(SuspenseContext);
553-
const track = { loading: true, error: undefined };
566+
const track = { _loading: true, error: undefined };
554567
if (ctx) {
555568
ctx.resources.set(id, track);
556569
contexts.add(ctx);
557570
}
558571
if (sharedConfig.context!.async) {
559572
sharedConfig.context!.block(
560573
p.then(() => {
561-
track.loading = false;
574+
track._loading = false;
562575
notifySuspense(contexts);
563576
})
564577
);
@@ -571,7 +584,7 @@ export function lazy<T extends Component<any>>(
571584

572585
function suspenseComplete(c: SuspenseContextType) {
573586
for (const r of c.resources.values()) {
574-
if (r.loading) return false;
587+
if (r._loading) return false;
575588
}
576589
return true;
577590
}
@@ -642,7 +655,7 @@ export function Suspense(props: { fallback?: string; children: string }) {
642655
const value: SuspenseContextType =
643656
ctx.suspense[id] ||
644657
(ctx.suspense[id] = {
645-
resources: new Map<string, { loading: boolean; error: any }>(),
658+
resources: new Map<string, { _loading: boolean; error: any }>(),
646659
completed: () => {
647660
const res = runSuspense();
648661
if (suspenseComplete(value)) {

0 commit comments

Comments
 (0)