@typed/template 0.2.0 → 0.3.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cjs/Directive.js +1 -1
- package/dist/cjs/Directive.js.map +1 -1
- package/dist/cjs/ElementRef.js +23 -13
- package/dist/cjs/ElementRef.js.map +1 -1
- package/dist/cjs/ElementSource.js +16 -18
- package/dist/cjs/ElementSource.js.map +1 -1
- package/dist/cjs/EventHandler.js +1 -1
- package/dist/cjs/EventHandler.js.map +1 -1
- package/dist/cjs/Html.js +31 -32
- package/dist/cjs/Html.js.map +1 -1
- package/dist/cjs/HtmlChunk.js +4 -1
- package/dist/cjs/HtmlChunk.js.map +1 -1
- package/dist/cjs/Hydrate.js +1 -1
- package/dist/cjs/Hydrate.js.map +1 -1
- package/dist/cjs/Many.js +14 -13
- package/dist/cjs/Many.js.map +1 -1
- package/dist/cjs/Parser.js +11 -323
- package/dist/cjs/Parser.js.map +1 -1
- package/dist/cjs/Placeholder.js +3 -3
- package/dist/cjs/Placeholder.js.map +1 -1
- package/dist/cjs/Platform.js +4 -4
- package/dist/cjs/Platform.js.map +1 -1
- package/dist/cjs/Render.js +1 -1
- package/dist/cjs/Render.js.map +1 -1
- package/dist/cjs/RenderContext.js +48 -27
- package/dist/cjs/RenderContext.js.map +1 -1
- package/dist/cjs/RenderTemplate.js +2 -17
- package/dist/cjs/RenderTemplate.js.map +1 -1
- package/dist/cjs/Template.js +27 -1
- package/dist/cjs/Template.js.map +1 -1
- package/dist/cjs/TemplateInstance.js +2 -2
- package/dist/cjs/TemplateInstance.js.map +1 -1
- package/dist/cjs/Test.js +20 -7
- package/dist/cjs/Test.js.map +1 -1
- package/dist/cjs/index.js +0 -12
- package/dist/cjs/index.js.map +1 -1
- package/dist/cjs/internal/EventSource.js +95 -0
- package/dist/cjs/internal/EventSource.js.map +1 -0
- package/dist/cjs/internal/browser.js +11 -11
- package/dist/cjs/internal/browser.js.map +1 -1
- package/dist/cjs/internal/chunks.js +4 -1
- package/dist/cjs/internal/chunks.js.map +1 -1
- package/dist/cjs/internal/errors.js +4 -0
- package/dist/cjs/internal/errors.js.map +1 -1
- package/dist/cjs/internal/hydrate.js +113 -80
- package/dist/cjs/internal/hydrate.js.map +1 -1
- package/dist/cjs/internal/indexRefCounter.js +49 -2
- package/dist/cjs/internal/indexRefCounter.js.map +1 -1
- package/dist/cjs/internal/parser.js +72 -21
- package/dist/cjs/internal/parser.js.map +1 -1
- package/dist/cjs/internal/parts.js +128 -28
- package/dist/cjs/internal/parts.js.map +1 -1
- package/dist/cjs/internal/render.js +460 -161
- package/dist/cjs/internal/render.js.map +1 -1
- package/dist/cjs/internal/server.js +5 -2
- package/dist/cjs/internal/server.js.map +1 -1
- package/dist/dts/Directive.d.ts.map +1 -1
- package/dist/dts/ElementRef.d.ts +4 -2
- package/dist/dts/ElementRef.d.ts.map +1 -1
- package/dist/dts/ElementSource.d.ts +10 -5
- package/dist/dts/ElementSource.d.ts.map +1 -1
- package/dist/dts/EventHandler.d.ts.map +1 -1
- package/dist/dts/Html.d.ts +1 -1
- package/dist/dts/Html.d.ts.map +1 -1
- package/dist/dts/HtmlChunk.d.ts.map +1 -1
- package/dist/dts/Many.d.ts +13 -11
- package/dist/dts/Many.d.ts.map +1 -1
- package/dist/dts/Parser.d.ts +3 -6
- package/dist/dts/Parser.d.ts.map +1 -1
- package/dist/dts/Part.d.ts +13 -3
- package/dist/dts/Part.d.ts.map +1 -1
- package/dist/dts/Placeholder.d.ts +2 -2
- package/dist/dts/Placeholder.d.ts.map +1 -1
- package/dist/dts/Render.d.ts +2 -1
- package/dist/dts/Render.d.ts.map +1 -1
- package/dist/dts/RenderContext.d.ts +5 -4
- package/dist/dts/RenderContext.d.ts.map +1 -1
- package/dist/dts/RenderTemplate.d.ts +2 -16
- package/dist/dts/RenderTemplate.d.ts.map +1 -1
- package/dist/dts/Renderable.d.ts +2 -2
- package/dist/dts/Renderable.d.ts.map +1 -1
- package/dist/dts/Template.d.ts +21 -3
- package/dist/dts/Template.d.ts.map +1 -1
- package/dist/dts/TemplateInstance.d.ts +3 -2
- package/dist/dts/TemplateInstance.d.ts.map +1 -1
- package/dist/dts/Test.d.ts +4 -6
- package/dist/dts/Test.d.ts.map +1 -1
- package/dist/dts/index.d.ts +0 -4
- package/dist/dts/index.d.ts.map +1 -1
- package/dist/dts/internal/EventSource.d.ts +12 -0
- package/dist/dts/internal/EventSource.d.ts.map +1 -0
- package/dist/dts/internal/browser.d.ts.map +1 -1
- package/dist/dts/internal/chunks.d.ts +1 -0
- package/dist/dts/internal/chunks.d.ts.map +1 -1
- package/dist/dts/internal/errors.d.ts +1 -0
- package/dist/dts/internal/errors.d.ts.map +1 -1
- package/dist/dts/internal/hydrate.d.ts +9 -16
- package/dist/dts/internal/hydrate.d.ts.map +1 -1
- package/dist/dts/internal/indexRefCounter.d.ts +5 -0
- package/dist/dts/internal/indexRefCounter.d.ts.map +1 -1
- package/dist/dts/internal/module-augmentation.d.ts +0 -4
- package/dist/dts/internal/module-augmentation.d.ts.map +1 -1
- package/dist/dts/internal/parser.d.ts +8 -0
- package/dist/dts/internal/parser.d.ts.map +1 -1
- package/dist/dts/internal/parts.d.ts +66 -56
- package/dist/dts/internal/parts.d.ts.map +1 -1
- package/dist/dts/internal/render.d.ts +1 -15
- package/dist/dts/internal/render.d.ts.map +1 -1
- package/dist/dts/internal/server.d.ts.map +1 -1
- package/dist/esm/Directive.js +1 -1
- package/dist/esm/Directive.js.map +1 -1
- package/dist/esm/ElementRef.js +12 -7
- package/dist/esm/ElementRef.js.map +1 -1
- package/dist/esm/ElementSource.js +16 -13
- package/dist/esm/ElementSource.js.map +1 -1
- package/dist/esm/EventHandler.js +1 -1
- package/dist/esm/EventHandler.js.map +1 -1
- package/dist/esm/Html.js +29 -24
- package/dist/esm/Html.js.map +1 -1
- package/dist/esm/HtmlChunk.js +6 -1
- package/dist/esm/HtmlChunk.js.map +1 -1
- package/dist/esm/Hydrate.js +1 -1
- package/dist/esm/Hydrate.js.map +1 -1
- package/dist/esm/Many.js +14 -10
- package/dist/esm/Many.js.map +1 -1
- package/dist/esm/Parser.js +6 -335
- package/dist/esm/Parser.js.map +1 -1
- package/dist/esm/Placeholder.js +2 -2
- package/dist/esm/Placeholder.js.map +1 -1
- package/dist/esm/Platform.js +2 -2
- package/dist/esm/Platform.js.map +1 -1
- package/dist/esm/Render.js +1 -1
- package/dist/esm/Render.js.map +1 -1
- package/dist/esm/RenderContext.js +38 -17
- package/dist/esm/RenderContext.js.map +1 -1
- package/dist/esm/RenderTemplate.js +2 -12
- package/dist/esm/RenderTemplate.js.map +1 -1
- package/dist/esm/Template.js +24 -0
- package/dist/esm/Template.js.map +1 -1
- package/dist/esm/TemplateInstance.js +2 -2
- package/dist/esm/TemplateInstance.js.map +1 -1
- package/dist/esm/Test.js +20 -7
- package/dist/esm/Test.js.map +1 -1
- package/dist/esm/index.js +0 -4
- package/dist/esm/index.js.map +1 -1
- package/dist/esm/internal/EventSource.js +91 -0
- package/dist/esm/internal/EventSource.js.map +1 -0
- package/dist/esm/internal/browser.js +12 -12
- package/dist/esm/internal/browser.js.map +1 -1
- package/dist/esm/internal/chunks.js +2 -0
- package/dist/esm/internal/chunks.js.map +1 -1
- package/dist/esm/internal/errors.js +3 -0
- package/dist/esm/internal/errors.js.map +1 -1
- package/dist/esm/internal/hydrate.js +113 -76
- package/dist/esm/internal/hydrate.js.map +1 -1
- package/dist/esm/internal/indexRefCounter.js +50 -2
- package/dist/esm/internal/indexRefCounter.js.map +1 -1
- package/dist/esm/internal/parser.js +98 -22
- package/dist/esm/internal/parser.js.map +1 -1
- package/dist/esm/internal/parts.js +110 -27
- package/dist/esm/internal/parts.js.map +1 -1
- package/dist/esm/internal/render.js +446 -157
- package/dist/esm/internal/render.js.map +1 -1
- package/dist/esm/internal/server.js +5 -4
- package/dist/esm/internal/server.js.map +1 -1
- package/package.json +10 -26
- package/src/Directive.ts +1 -1
- package/src/ElementRef.ts +18 -14
- package/src/ElementSource.ts +62 -47
- package/src/EventHandler.ts +1 -1
- package/src/Html.ts +58 -57
- package/src/HtmlChunk.ts +15 -1
- package/src/Hydrate.ts +1 -1
- package/src/Many.ts +53 -43
- package/src/Parser.ts +10 -453
- package/src/Part.ts +15 -3
- package/src/Placeholder.ts +4 -4
- package/src/Platform.ts +2 -2
- package/src/Render.ts +7 -2
- package/src/RenderContext.ts +47 -19
- package/src/RenderTemplate.ts +9 -54
- package/src/Renderable.ts +2 -1
- package/src/Template.ts +26 -0
- package/src/TemplateInstance.ts +9 -9
- package/src/Test.ts +40 -21
- package/src/index.ts +0 -4
- package/src/internal/EventSource.ts +153 -0
- package/src/internal/browser.ts +26 -25
- package/src/internal/chunks.ts +4 -0
- package/src/internal/errors.ts +4 -0
- package/src/internal/hydrate.ts +161 -107
- package/src/internal/indexRefCounter.ts +63 -2
- package/src/internal/module-augmentation.ts +0 -4
- package/src/internal/parser.ts +107 -25
- package/src/internal/parts.ts +158 -73
- package/src/internal/render.ts +638 -289
- package/src/internal/server.ts +5 -3
- package/Token/package.json +0 -6
- package/Tokenizer/package.json +0 -6
- package/dist/cjs/Token.js +0 -270
- package/dist/cjs/Token.js.map +0 -1
- package/dist/cjs/Tokenizer.js +0 -18
- package/dist/cjs/Tokenizer.js.map +0 -1
- package/dist/cjs/internal/readAttribute.js +0 -34
- package/dist/cjs/internal/readAttribute.js.map +0 -1
- package/dist/cjs/internal/tokenizer.js +0 -264
- package/dist/cjs/internal/tokenizer.js.map +0 -1
- package/dist/dts/Token.d.ts +0 -202
- package/dist/dts/Token.d.ts.map +0 -1
- package/dist/dts/Tokenizer.d.ts +0 -6
- package/dist/dts/Tokenizer.d.ts.map +0 -1
- package/dist/dts/internal/readAttribute.d.ts +0 -9
- package/dist/dts/internal/readAttribute.d.ts.map +0 -1
- package/dist/dts/internal/tokenizer.d.ts +0 -3
- package/dist/dts/internal/tokenizer.d.ts.map +0 -1
- package/dist/esm/Token.js +0 -264
- package/dist/esm/Token.js.map +0 -1
- package/dist/esm/Tokenizer.js +0 -9
- package/dist/esm/Tokenizer.js.map +0 -1
- package/dist/esm/internal/readAttribute.js +0 -24
- package/dist/esm/internal/readAttribute.js.map +0 -1
- package/dist/esm/internal/tokenizer.js +0 -296
- package/dist/esm/internal/tokenizer.js.map +0 -1
- package/src/Token.ts +0 -269
- package/src/Tokenizer.ts +0 -10
- package/src/internal/readAttribute.ts +0 -28
- package/src/internal/tokenizer.ts +0 -338
package/src/internal/hydrate.ts
CHANGED
|
@@ -1,23 +1,23 @@
|
|
|
1
1
|
import * as Fx from "@typed/fx/Fx"
|
|
2
|
-
import * as
|
|
3
|
-
import type { Rendered } from "@typed/wire"
|
|
4
|
-
import type { Cause } from "effect"
|
|
5
|
-
import { Effect } from "effect"
|
|
6
|
-
import * as ElementRef from "../ElementRef.js"
|
|
2
|
+
import * as Effect from "effect/Effect"
|
|
7
3
|
import type { Placeholder } from "../Placeholder.js"
|
|
8
4
|
import type { Renderable } from "../Renderable.js"
|
|
9
5
|
import type { RenderContext } from "../RenderContext.js"
|
|
6
|
+
import type { RenderEvent } from "../RenderEvent.js"
|
|
10
7
|
import { DomRenderEvent } from "../RenderEvent.js"
|
|
11
8
|
import type { RenderTemplate } from "../RenderTemplate.js"
|
|
12
|
-
import {
|
|
13
|
-
import { indexRefCounter } from "./indexRefCounter.js"
|
|
9
|
+
import { indexRefCounter2 } from "./indexRefCounter.js"
|
|
14
10
|
|
|
15
11
|
import { unsafeGet } from "@typed/context"
|
|
16
12
|
|
|
13
|
+
import { Either } from "effect"
|
|
14
|
+
import { Scope } from "effect/Scope"
|
|
17
15
|
import type { Template } from "../Template.js"
|
|
18
16
|
import { CouldNotFindCommentError, CouldNotFindRootElement } from "./errors.js"
|
|
17
|
+
import { makeEventSource } from "./EventSource.js"
|
|
19
18
|
import { HydrateContext } from "./HydrateContext.js"
|
|
20
|
-
import {
|
|
19
|
+
import type { RenderPartContext } from "./render.js"
|
|
20
|
+
import { getBrowserEntry, renderPart2, renderTemplate } from "./render.js"
|
|
21
21
|
import {
|
|
22
22
|
findPath,
|
|
23
23
|
getPreviousNodes,
|
|
@@ -27,67 +27,105 @@ import {
|
|
|
27
27
|
type ParentChildNodes
|
|
28
28
|
} from "./utils.js"
|
|
29
29
|
|
|
30
|
-
// TODO: Handle missing comment errors
|
|
31
|
-
|
|
32
30
|
/**
|
|
33
31
|
* Here for "standard" browser rendering, a TemplateInstance is effectively a live
|
|
34
32
|
* view into the contents rendered by the Template.
|
|
35
33
|
*/
|
|
36
|
-
export const hydrateTemplate: (document: Document, ctx: RenderContext) => RenderTemplate =
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
providedRef?: ElementRef.ElementRef<T>
|
|
42
|
-
) => {
|
|
43
|
-
return Effect.gen(function*(_) {
|
|
44
|
-
const context = yield* _(Effect.context<never>())
|
|
45
|
-
const hydrateCtx = unsafeGet(context, HydrateContext)
|
|
46
|
-
|
|
47
|
-
// If we're not longer hydrating, just render normally
|
|
48
|
-
if (!hydrateCtx.hydrate) {
|
|
49
|
-
return yield* _(renderTemplate(document, renderContext)(templateStrings, values, providedRef))
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
const elementRef = providedRef || (yield* _(ElementRef.make<T>()))
|
|
53
|
-
const events = Fx.map(elementRef, DomRenderEvent)
|
|
54
|
-
const errors = Subject.make<Placeholder.Error<Values[number]>, never>()
|
|
55
|
-
|
|
56
|
-
const { getParts, template, where, wire } = getHydrateEntry({
|
|
57
|
-
...hydrateCtx,
|
|
58
|
-
document,
|
|
59
|
-
renderContext,
|
|
60
|
-
elementRef,
|
|
61
|
-
strings: templateStrings,
|
|
62
|
-
onCause: errors.onFailure
|
|
63
|
-
})
|
|
64
|
-
const parts = yield* _(getParts)
|
|
65
|
-
|
|
66
|
-
// If there are parts we need to render them before constructing our Wire
|
|
67
|
-
if (parts.length > 0) {
|
|
68
|
-
const refCounter = yield* _(indexRefCounter(parts.length))
|
|
34
|
+
export const hydrateTemplate: (document: Document, ctx: RenderContext) => RenderTemplate = (
|
|
35
|
+
document,
|
|
36
|
+
renderContext
|
|
37
|
+
) => {
|
|
38
|
+
const render_ = renderTemplate(document, renderContext)
|
|
69
39
|
|
|
70
|
-
|
|
71
|
-
|
|
40
|
+
return <Values extends ReadonlyArray<Renderable<any, any>>>(
|
|
41
|
+
templateStrings: TemplateStringsArray,
|
|
42
|
+
values: Values
|
|
43
|
+
): Fx.Fx<
|
|
44
|
+
Scope | Placeholder.Context<Values[number]>,
|
|
45
|
+
Placeholder.Error<Values[number]>,
|
|
46
|
+
RenderEvent
|
|
47
|
+
> => {
|
|
48
|
+
return Fx.make((sink) =>
|
|
49
|
+
Effect.gen(function*(_) {
|
|
50
|
+
const context = yield* _(Effect.context<Scope>())
|
|
51
|
+
const hydrateCtx = unsafeGet(context, HydrateContext)
|
|
52
|
+
const scope = unsafeGet(context, Scope)
|
|
53
|
+
|
|
54
|
+
// If we're not longer hydrating, just render normally
|
|
55
|
+
if (hydrateCtx.hydrate === false) {
|
|
56
|
+
return render_(templateStrings, values)
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
const either = getHydrateEntry({
|
|
60
|
+
...hydrateCtx,
|
|
61
|
+
document,
|
|
62
|
+
renderContext,
|
|
63
|
+
strings: templateStrings
|
|
64
|
+
})
|
|
65
|
+
|
|
66
|
+
if (Either.isLeft(either)) {
|
|
67
|
+
hydrateCtx.hydrate = false
|
|
68
|
+
return render_(templateStrings, values)
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
const { template, where, wire } = either.right
|
|
72
|
+
|
|
73
|
+
if (values.length === 0) return yield* _(sink.onSuccess(DomRenderEvent(wire)), Effect.zipRight(Effect.never))
|
|
74
|
+
|
|
75
|
+
const makeHydrateContext = (index: number): HydrateContext => ({
|
|
72
76
|
where,
|
|
73
77
|
rootIndex: index,
|
|
74
78
|
parentTemplate: template,
|
|
75
79
|
hydrate: true
|
|
76
|
-
})
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
80
|
+
})
|
|
81
|
+
|
|
82
|
+
const refCounter = yield* _(indexRefCounter2())
|
|
83
|
+
const ctx: RenderPartContext = {
|
|
84
|
+
context,
|
|
85
|
+
document,
|
|
86
|
+
eventSource: makeEventSource(),
|
|
87
|
+
expected: 0,
|
|
88
|
+
refCounter,
|
|
89
|
+
renderContext,
|
|
90
|
+
onCause: sink.onFailure,
|
|
91
|
+
values,
|
|
92
|
+
makeHydrateContext
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
// Connect our interpolated values to our template parts
|
|
96
|
+
const effects: Array<Effect.Effect<Scope | Placeholder.Context<Values[number]>, never, void>> = []
|
|
97
|
+
for (const [part, path] of template.parts) {
|
|
98
|
+
const eff = renderPart2(part, where, path, ctx)
|
|
99
|
+
if (eff !== null) {
|
|
100
|
+
effects.push(
|
|
101
|
+
...(Array.isArray(eff) ? eff : [eff]) as Array<
|
|
102
|
+
Effect.Effect<Scope | Placeholder.Context<Values[number]>, never, void>
|
|
103
|
+
>
|
|
104
|
+
)
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
// Fork any effects necessary
|
|
109
|
+
if (effects.length > 0) {
|
|
110
|
+
yield* _(Effect.forkAll(effects))
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
// Set the element when it is ready
|
|
114
|
+
yield* _(ctx.eventSource.setup(wire, scope))
|
|
115
|
+
|
|
116
|
+
// Emit our DomRenderEvent
|
|
117
|
+
yield* _(sink.onSuccess(DomRenderEvent(wire)))
|
|
118
|
+
|
|
119
|
+
// Stop hydrating
|
|
120
|
+
hydrateCtx.hydrate = false
|
|
121
|
+
|
|
122
|
+
// Ensure our templates last forever in the DOM environment
|
|
123
|
+
// so event listeners are kept attached to the current Scope.
|
|
124
|
+
yield* _(Effect.never)
|
|
125
|
+
})
|
|
126
|
+
)
|
|
90
127
|
}
|
|
128
|
+
}
|
|
91
129
|
|
|
92
130
|
export function findRootParentChildNodes(where: HTMLElement): ParentChildNodes {
|
|
93
131
|
const childNodes = findRootChildNodes(where)
|
|
@@ -103,65 +141,76 @@ const END = "typed-end"
|
|
|
103
141
|
|
|
104
142
|
// Finds all of the childNodes between the "typed-start" and "typed-end" comments
|
|
105
143
|
export function findRootChildNodes(where: HTMLElement): Array<Node> {
|
|
106
|
-
|
|
144
|
+
let start = -1
|
|
145
|
+
let end = -1
|
|
107
146
|
|
|
108
|
-
|
|
109
|
-
|
|
147
|
+
const { childNodes } = where
|
|
148
|
+
const length = childNodes.length
|
|
110
149
|
|
|
111
|
-
for (let i = 0; i <
|
|
112
|
-
const node =
|
|
150
|
+
for (let i = 0; i < length; i++) {
|
|
151
|
+
const node = childNodes[i]
|
|
113
152
|
|
|
114
|
-
if (node.nodeType === node.COMMENT_NODE) {
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
break
|
|
118
|
-
}
|
|
153
|
+
if (node.nodeType === node.COMMENT_NODE && node.nodeValue === START) {
|
|
154
|
+
start = i
|
|
155
|
+
break
|
|
119
156
|
}
|
|
120
157
|
}
|
|
121
158
|
|
|
122
|
-
for (let i =
|
|
123
|
-
const node =
|
|
159
|
+
for (let i = length - 1; i >= start; i--) {
|
|
160
|
+
const node = childNodes[i]
|
|
124
161
|
|
|
125
|
-
if (node.nodeType === node.COMMENT_NODE) {
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
break
|
|
129
|
-
}
|
|
162
|
+
if (node.nodeType === node.COMMENT_NODE && node.nodeValue === END) {
|
|
163
|
+
end = i
|
|
164
|
+
break
|
|
130
165
|
}
|
|
131
166
|
}
|
|
132
167
|
|
|
133
|
-
|
|
134
|
-
|
|
168
|
+
// If we can't find the start and end comments, just return all childNodes
|
|
169
|
+
if (start === -1 && end === -1) {
|
|
170
|
+
return Array.from(childNodes)
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
start = start === -1 ? 0 : start
|
|
174
|
+
end = end === -1 ? length - 1 : end
|
|
175
|
+
|
|
176
|
+
const rootChildNodes: Array<Node> = Array(end - start)
|
|
177
|
+
|
|
178
|
+
for (let i = start + 1, j = 0; i <= end; i++) {
|
|
179
|
+
rootChildNodes[j++] = childNodes[i]
|
|
135
180
|
}
|
|
136
181
|
|
|
137
|
-
return
|
|
182
|
+
return rootChildNodes
|
|
138
183
|
}
|
|
139
184
|
|
|
140
185
|
export function findTemplateResultPartChildNodes(
|
|
141
186
|
where: ParentChildNodes,
|
|
142
187
|
parentTemplate: Template,
|
|
143
|
-
childTemplate: Template
|
|
188
|
+
childTemplate: Template,
|
|
144
189
|
partIndex: number,
|
|
145
190
|
childIndex?: number
|
|
146
|
-
) {
|
|
191
|
+
): Either.Either<CouldNotFindRootElement | CouldNotFindCommentError, ParentChildNodes> {
|
|
147
192
|
const [, path] = parentTemplate.parts[partIndex]
|
|
148
193
|
const parentNode = findPath(where, path) as HTMLElement
|
|
149
|
-
const
|
|
194
|
+
const childNodesEither = findPartChildNodes(parentNode, childTemplate.hash, partIndex)
|
|
195
|
+
if (Either.isLeft(childNodesEither)) return Either.left(childNodesEither.left)
|
|
196
|
+
|
|
197
|
+
const childNodes = childNodesEither.right
|
|
150
198
|
const parentChildNodes = {
|
|
151
199
|
parentNode,
|
|
152
200
|
childNodes: childIndex !== undefined ? [childNodes[childIndex]] : childNodes
|
|
153
201
|
}
|
|
154
202
|
|
|
155
|
-
return parentChildNodes
|
|
203
|
+
return Either.right(parentChildNodes)
|
|
156
204
|
}
|
|
157
205
|
|
|
158
206
|
export function findPartChildNodes(
|
|
159
207
|
{ childNodes }: ParentChildNodes,
|
|
160
|
-
hash: string
|
|
208
|
+
hash: string,
|
|
161
209
|
partIndex: number
|
|
162
|
-
) {
|
|
163
|
-
const
|
|
164
|
-
|
|
210
|
+
): Either.Either<CouldNotFindRootElement | CouldNotFindCommentError, Array<Node>> {
|
|
211
|
+
const either = findPartComment(childNodes, partIndex)
|
|
212
|
+
if (Either.isLeft(either)) return Either.left(either.left)
|
|
213
|
+
const [comment, index] = either.right
|
|
165
214
|
const nodes: Array<Node> = []
|
|
166
215
|
const previousHoleValue = `hole${partIndex - 1}`
|
|
167
216
|
|
|
@@ -176,37 +225,38 @@ export function findPartChildNodes(
|
|
|
176
225
|
}
|
|
177
226
|
}
|
|
178
227
|
} else {
|
|
179
|
-
return [...getPreviousNodes(comment, partIndex), comment]
|
|
228
|
+
return Either.right([...getPreviousNodes(comment, partIndex), comment])
|
|
180
229
|
}
|
|
181
230
|
|
|
182
231
|
if (nodes.length === 0) {
|
|
183
|
-
|
|
232
|
+
return Either.left(new CouldNotFindRootElement(partIndex))
|
|
184
233
|
}
|
|
185
234
|
|
|
186
235
|
nodes.push(comment)
|
|
187
236
|
|
|
188
|
-
return nodes
|
|
237
|
+
return Either.right(nodes)
|
|
189
238
|
}
|
|
190
239
|
|
|
191
|
-
export function findPartComment(
|
|
240
|
+
export function findPartComment(
|
|
241
|
+
childNodes: ArrayLike<Node>,
|
|
242
|
+
partIndex: number
|
|
243
|
+
): Either.Either<CouldNotFindCommentError, readonly [Comment, number]> {
|
|
192
244
|
const search = partIndex === -1 ? `typed-end` : `hole${partIndex}`
|
|
193
245
|
|
|
194
246
|
for (let i = 0; i < childNodes.length; ++i) {
|
|
195
247
|
const node = childNodes[i]
|
|
196
248
|
|
|
197
249
|
if (isCommentWithValue(node, search)) {
|
|
198
|
-
return [node, i] as const
|
|
250
|
+
return Either.right([node, i] as const)
|
|
199
251
|
}
|
|
200
252
|
}
|
|
201
253
|
|
|
202
|
-
|
|
254
|
+
return Either.left(new CouldNotFindCommentError(partIndex))
|
|
203
255
|
}
|
|
204
256
|
|
|
205
257
|
export function getHydrateEntry({
|
|
206
258
|
childIndex,
|
|
207
259
|
document,
|
|
208
|
-
elementRef,
|
|
209
|
-
onCause,
|
|
210
260
|
parentTemplate,
|
|
211
261
|
renderContext,
|
|
212
262
|
rootIndex,
|
|
@@ -219,18 +269,21 @@ export function getHydrateEntry({
|
|
|
219
269
|
rootIndex: number
|
|
220
270
|
parentTemplate: Template | null
|
|
221
271
|
strings: TemplateStringsArray
|
|
222
|
-
elementRef: ElementRef.ElementRef<any>
|
|
223
|
-
onCause: (cause: Cause.Cause<any>) => Effect.Effect<never, never, void>
|
|
224
272
|
childIndex?: number
|
|
225
|
-
})
|
|
273
|
+
}): Either.Either<
|
|
274
|
+
CouldNotFindRootElement | CouldNotFindCommentError,
|
|
275
|
+
{ readonly template: Template; readonly wire: Node | Array<Node>; readonly where: ParentChildNodes }
|
|
276
|
+
> {
|
|
226
277
|
const { template } = getBrowserEntry(document, renderContext, strings)
|
|
227
278
|
|
|
228
279
|
if (parentTemplate) {
|
|
229
|
-
|
|
280
|
+
const either = findTemplateResultPartChildNodes(where, parentTemplate, template, rootIndex, childIndex)
|
|
281
|
+
if (Either.isLeft(either)) {
|
|
282
|
+
return Either.left(either.left)
|
|
283
|
+
}
|
|
284
|
+
where = either.right
|
|
230
285
|
}
|
|
231
286
|
|
|
232
|
-
const getParts = buildParts(document, renderContext, template, where, elementRef, onCause, true)
|
|
233
|
-
|
|
234
287
|
const wire = (() => {
|
|
235
288
|
if (!parentTemplate) {
|
|
236
289
|
const childNodes = Array.from(where.childNodes).filter((node) =>
|
|
@@ -253,10 +306,11 @@ export function getHydrateEntry({
|
|
|
253
306
|
)
|
|
254
307
|
})()
|
|
255
308
|
|
|
256
|
-
return
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
309
|
+
return Either.right(
|
|
310
|
+
{
|
|
311
|
+
template,
|
|
312
|
+
wire,
|
|
313
|
+
where
|
|
314
|
+
} as const
|
|
315
|
+
)
|
|
262
316
|
}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import * as Deferred from "effect/Deferred"
|
|
2
2
|
import * as Effect from "effect/Effect"
|
|
3
|
+
import * as Option from "effect/Option"
|
|
3
4
|
|
|
4
5
|
export type IndexRefCounter = {
|
|
5
6
|
release: (index: number) => Effect.Effect<never, never, void>
|
|
@@ -15,13 +16,16 @@ export function indexRefCounter(expected: number): Effect.Effect<
|
|
|
15
16
|
IndexRefCounter
|
|
16
17
|
> {
|
|
17
18
|
return Effect.map(Deferred.make<never, void>(), (deferred) => {
|
|
19
|
+
const done = Deferred.succeed(deferred, undefined)
|
|
18
20
|
const indexes = new Set<number>(Array.from({ length: expected }, (_, i) => i))
|
|
19
21
|
|
|
20
22
|
function release(index: number) {
|
|
21
23
|
return Effect.suspend(() => {
|
|
22
24
|
if (indexes.delete(index) && indexes.size === 0) {
|
|
23
|
-
return
|
|
24
|
-
} else
|
|
25
|
+
return done
|
|
26
|
+
} else {
|
|
27
|
+
return Effect.unit
|
|
28
|
+
}
|
|
25
29
|
})
|
|
26
30
|
}
|
|
27
31
|
|
|
@@ -31,3 +35,60 @@ export function indexRefCounter(expected: number): Effect.Effect<
|
|
|
31
35
|
}
|
|
32
36
|
})
|
|
33
37
|
}
|
|
38
|
+
|
|
39
|
+
export type IndexRefCounter2 = {
|
|
40
|
+
release: (index: number) => Effect.Effect<never, never, void>
|
|
41
|
+
expect: (count: number) => Effect.Effect<never, never, boolean>
|
|
42
|
+
wait: Effect.Effect<never, never, void>
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
/**
|
|
46
|
+
* @internal
|
|
47
|
+
*/
|
|
48
|
+
export function indexRefCounter2(): Effect.Effect<
|
|
49
|
+
never,
|
|
50
|
+
never,
|
|
51
|
+
IndexRefCounter2
|
|
52
|
+
> {
|
|
53
|
+
return Effect.map(Deferred.make<never, void>(), (deferred) => {
|
|
54
|
+
let expected: Option.Option<number> = Option.none<number>()
|
|
55
|
+
const done = Deferred.succeed(deferred, undefined)
|
|
56
|
+
const indexes = new Set<number>()
|
|
57
|
+
|
|
58
|
+
function isDone() {
|
|
59
|
+
if (Option.isSome(expected)) {
|
|
60
|
+
return indexes.size === expected.value
|
|
61
|
+
} else {
|
|
62
|
+
return false
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
function release(index: number) {
|
|
67
|
+
return Effect.suspend(() => {
|
|
68
|
+
indexes.add(index)
|
|
69
|
+
if (isDone()) {
|
|
70
|
+
return done
|
|
71
|
+
} else {
|
|
72
|
+
return Effect.succeed(false)
|
|
73
|
+
}
|
|
74
|
+
})
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
function expect(count: number) {
|
|
78
|
+
return Effect.suspend(() => {
|
|
79
|
+
expected = Option.some(count)
|
|
80
|
+
if (isDone()) {
|
|
81
|
+
return Effect.as(done, false)
|
|
82
|
+
} else {
|
|
83
|
+
return Effect.succeed(true)
|
|
84
|
+
}
|
|
85
|
+
})
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
return {
|
|
89
|
+
release,
|
|
90
|
+
expect,
|
|
91
|
+
wait: Deferred.await(deferred)
|
|
92
|
+
}
|
|
93
|
+
})
|
|
94
|
+
}
|