@k8ts/instruments 0.1.0
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/LICENSE.md +7 -0
- package/README.md +3 -0
- package/dist/_embedder/base.d.ts +11 -0
- package/dist/_embedder/base.d.ts.map +1 -0
- package/dist/_embedder/base.js +39 -0
- package/dist/_embedder/base.js.map +1 -0
- package/dist/_embedder/index.d.ts +2 -0
- package/dist/_embedder/index.d.ts.map +1 -0
- package/dist/_embedder/index.js +18 -0
- package/dist/_embedder/index.js.map +1 -0
- package/dist/_string/index.d.ts +6 -0
- package/dist/_string/index.d.ts.map +1 -0
- package/dist/_string/index.js +22 -0
- package/dist/_string/index.js.map +1 -0
- package/dist/_string/markers.d.ts +3 -0
- package/dist/_string/markers.d.ts.map +1 -0
- package/dist/_string/markers.js +48 -0
- package/dist/_string/markers.js.map +1 -0
- package/dist/_string/post-processor.d.ts +7 -0
- package/dist/_string/post-processor.d.ts.map +1 -0
- package/dist/_string/post-processor.js +30 -0
- package/dist/_string/post-processor.js.map +1 -0
- package/dist/_string/pretty-objects.d.ts +27 -0
- package/dist/_string/pretty-objects.d.ts.map +1 -0
- package/dist/_string/pretty-objects.js +192 -0
- package/dist/_string/pretty-objects.js.map +1 -0
- package/dist/_string/pretty-print.d.ts +2 -0
- package/dist/_string/pretty-print.d.ts.map +1 -0
- package/dist/_string/pretty-print.js +27 -0
- package/dist/_string/pretty-print.js.map +1 -0
- package/dist/_string/super-script.d.ts +2 -0
- package/dist/_string/super-script.d.ts.map +1 -0
- package/dist/_string/super-script.js +20 -0
- package/dist/_string/super-script.js.map +1 -0
- package/dist/api-kind/index.d.ts +43 -0
- package/dist/api-kind/index.d.ts.map +1 -0
- package/dist/api-kind/index.js +102 -0
- package/dist/api-kind/index.js.map +1 -0
- package/dist/cmd/cli-command.d.ts +23 -0
- package/dist/cmd/cli-command.d.ts.map +1 -0
- package/dist/cmd/cli-command.js +73 -0
- package/dist/cmd/cli-command.js.map +1 -0
- package/dist/cmd/cli-term.d.ts +25 -0
- package/dist/cmd/cli-term.d.ts.map +1 -0
- package/dist/cmd/cli-term.js +55 -0
- package/dist/cmd/cli-term.js.map +1 -0
- package/dist/cmd/index.d.ts +3 -0
- package/dist/cmd/index.d.ts.map +1 -0
- package/dist/cmd/index.js +7 -0
- package/dist/cmd/index.js.map +1 -0
- package/dist/cmd/types.d.ts +5 -0
- package/dist/cmd/types.d.ts.map +1 -0
- package/dist/cmd/types.js +3 -0
- package/dist/cmd/types.js.map +1 -0
- package/dist/displayers/displayers.d.ts +33 -0
- package/dist/displayers/displayers.d.ts.map +1 -0
- package/dist/displayers/displayers.js +129 -0
- package/dist/displayers/displayers.js.map +1 -0
- package/dist/displayers/index.d.ts +2 -0
- package/dist/displayers/index.d.ts.map +1 -0
- package/dist/displayers/index.js +18 -0
- package/dist/displayers/index.js.map +1 -0
- package/dist/env/env.d.ts +20 -0
- package/dist/env/env.d.ts.map +1 -0
- package/dist/env/env.js +68 -0
- package/dist/env/env.js.map +1 -0
- package/dist/env/index.d.ts +3 -0
- package/dist/env/index.d.ts.map +1 -0
- package/dist/env/index.js +7 -0
- package/dist/env/index.js.map +1 -0
- package/dist/env/types.d.ts +4 -0
- package/dist/env/types.d.ts.map +1 -0
- package/dist/env/types.js +3 -0
- package/dist/env/types.js.map +1 -0
- package/dist/env/validate-name.d.ts +2 -0
- package/dist/env/validate-name.d.ts.map +1 -0
- package/dist/env/validate-name.js +12 -0
- package/dist/env/validate-name.js.map +1 -0
- package/dist/error.d.ts +8 -0
- package/dist/error.d.ts.map +1 -0
- package/dist/error.js +20 -0
- package/dist/error.js.map +1 -0
- package/dist/forward-exports/delayed-exports.d.ts +18 -0
- package/dist/forward-exports/delayed-exports.d.ts.map +1 -0
- package/dist/forward-exports/delayed-exports.js +119 -0
- package/dist/forward-exports/delayed-exports.js.map +1 -0
- package/dist/forward-exports/index.d.ts +2 -0
- package/dist/forward-exports/index.d.ts.map +1 -0
- package/dist/forward-exports/index.js +18 -0
- package/dist/forward-exports/index.js.map +1 -0
- package/dist/graph/base-node.d.ts +34 -0
- package/dist/graph/base-node.d.ts.map +1 -0
- package/dist/graph/base-node.js +102 -0
- package/dist/graph/base-node.js.map +1 -0
- package/dist/graph/base-origin-entity.d.ts +19 -0
- package/dist/graph/base-origin-entity.d.ts.map +1 -0
- package/dist/graph/base-origin-entity.js +105 -0
- package/dist/graph/base-origin-entity.js.map +1 -0
- package/dist/graph/dependencies.d.ts +12 -0
- package/dist/graph/dependencies.d.ts.map +1 -0
- package/dist/graph/dependencies.js +82 -0
- package/dist/graph/dependencies.js.map +1 -0
- package/dist/graph/index.d.ts +7 -0
- package/dist/graph/index.d.ts.map +1 -0
- package/dist/graph/index.js +23 -0
- package/dist/graph/index.js.map +1 -0
- package/dist/graph/origin-node.d.ts +32 -0
- package/dist/graph/origin-node.d.ts.map +1 -0
- package/dist/graph/origin-node.js +161 -0
- package/dist/graph/origin-node.js.map +1 -0
- package/dist/graph/relations.d.ts +26 -0
- package/dist/graph/relations.d.ts.map +1 -0
- package/dist/graph/relations.js +38 -0
- package/dist/graph/relations.js.map +1 -0
- package/dist/graph/resource-node.d.ts +28 -0
- package/dist/graph/resource-node.d.ts.map +1 -0
- package/dist/graph/resource-node.js +144 -0
- package/dist/graph/resource-node.js.map +1 -0
- package/dist/image/family.d.ts +26 -0
- package/dist/image/family.d.ts.map +1 -0
- package/dist/image/family.js +63 -0
- package/dist/image/family.js.map +1 -0
- package/dist/image/index.d.ts +2 -0
- package/dist/image/index.d.ts.map +1 -0
- package/dist/image/index.js +9 -0
- package/dist/image/index.js.map +1 -0
- package/dist/index.d.ts +19 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +35 -0
- package/dist/index.js.map +1 -0
- package/dist/kind-map/index.d.ts +44 -0
- package/dist/kind-map/index.d.ts.map +1 -0
- package/dist/kind-map/index.js +123 -0
- package/dist/kind-map/index.js.map +1 -0
- package/dist/manifest/index.d.ts +46 -0
- package/dist/manifest/index.d.ts.map +1 -0
- package/dist/manifest/index.js +21 -0
- package/dist/manifest/index.js.map +1 -0
- package/dist/manifest/manifest-builder.d.ts +45 -0
- package/dist/manifest/manifest-builder.d.ts.map +1 -0
- package/dist/manifest/manifest-builder.js +66 -0
- package/dist/manifest/manifest-builder.js.map +1 -0
- package/dist/ports/error.d.ts +5 -0
- package/dist/ports/error.d.ts.map +1 -0
- package/dist/ports/error.js +13 -0
- package/dist/ports/error.js.map +1 -0
- package/dist/ports/index.d.ts +7 -0
- package/dist/ports/index.d.ts.map +1 -0
- package/dist/ports/index.js +13 -0
- package/dist/ports/index.js.map +1 -0
- package/dist/ports/map.d.ts +13 -0
- package/dist/ports/map.d.ts.map +1 -0
- package/dist/ports/map.js +38 -0
- package/dist/ports/map.js.map +1 -0
- package/dist/ports/set.d.ts +18 -0
- package/dist/ports/set.d.ts.map +1 -0
- package/dist/ports/set.js +60 -0
- package/dist/ports/set.js.map +1 -0
- package/dist/ports/tools/entry.d.ts +6 -0
- package/dist/ports/tools/entry.d.ts.map +1 -0
- package/dist/ports/tools/entry.js +36 -0
- package/dist/ports/tools/entry.js.map +1 -0
- package/dist/ports/tools/parse.d.ts +3 -0
- package/dist/ports/tools/parse.d.ts.map +1 -0
- package/dist/ports/tools/parse.js +35 -0
- package/dist/ports/tools/parse.js.map +1 -0
- package/dist/ports/types.d.ts +37 -0
- package/dist/ports/types.d.ts.map +1 -0
- package/dist/ports/types.js +3 -0
- package/dist/ports/types.js.map +1 -0
- package/dist/producer/index.d.ts +2 -0
- package/dist/producer/index.d.ts.map +1 -0
- package/dist/producer/index.js +18 -0
- package/dist/producer/index.js.map +1 -0
- package/dist/producer/producer.d.ts +6 -0
- package/dist/producer/producer.d.ts.map +1 -0
- package/dist/producer/producer.js +13 -0
- package/dist/producer/producer.js.map +1 -0
- package/dist/ref-key/index.d.ts +2 -0
- package/dist/ref-key/index.d.ts.map +1 -0
- package/dist/ref-key/index.js +18 -0
- package/dist/ref-key/index.js.map +1 -0
- package/dist/ref-key/ref-key.d.ts +23 -0
- package/dist/ref-key/ref-key.d.ts.map +1 -0
- package/dist/ref-key/ref-key.js +67 -0
- package/dist/ref-key/ref-key.js.map +1 -0
- package/dist/reference/forward-ref.d.ts +22 -0
- package/dist/reference/forward-ref.d.ts.map +1 -0
- package/dist/reference/forward-ref.js +126 -0
- package/dist/reference/forward-ref.js.map +1 -0
- package/dist/reference/index.d.ts +4 -0
- package/dist/reference/index.d.ts.map +1 -0
- package/dist/reference/index.js +8 -0
- package/dist/reference/index.js.map +1 -0
- package/dist/reference/refable.d.ts +12 -0
- package/dist/reference/refable.d.ts.map +1 -0
- package/dist/reference/refable.js +3 -0
- package/dist/reference/refable.js.map +1 -0
- package/dist/resources/index.d.ts +3 -0
- package/dist/resources/index.d.ts.map +1 -0
- package/dist/resources/index.js +19 -0
- package/dist/resources/index.js.map +1 -0
- package/dist/resources/objects.d.ts +22 -0
- package/dist/resources/objects.d.ts.map +1 -0
- package/dist/resources/objects.js +93 -0
- package/dist/resources/objects.js.map +1 -0
- package/dist/resources/parser.d.ts +4 -0
- package/dist/resources/parser.d.ts.map +1 -0
- package/dist/resources/parser.js +21 -0
- package/dist/resources/parser.js.map +1 -0
- package/dist/resources/types.d.ts +18 -0
- package/dist/resources/types.d.ts.map +1 -0
- package/dist/resources/types.js +3 -0
- package/dist/resources/types.js.map +1 -0
- package/dist/src.tsbuildinfo +1 -0
- package/dist/test.tsbuildinfo +1 -0
- package/dist/tracing/git.d.ts +19 -0
- package/dist/tracing/git.d.ts.map +1 -0
- package/dist/tracing/git.js +45 -0
- package/dist/tracing/git.js.map +1 -0
- package/dist/tracing/index.d.ts +4 -0
- package/dist/tracing/index.d.ts.map +1 -0
- package/dist/tracing/index.js +20 -0
- package/dist/tracing/index.js.map +1 -0
- package/dist/tracing/trace.d.ts +11 -0
- package/dist/tracing/trace.d.ts.map +1 -0
- package/dist/tracing/trace.js +27 -0
- package/dist/tracing/trace.js.map +1 -0
- package/dist/tracing/traced.d.ts +4 -0
- package/dist/tracing/traced.d.ts.map +1 -0
- package/dist/tracing/traced.js +6 -0
- package/dist/tracing/traced.js.map +1 -0
- package/dist/units/index.d.ts +3 -0
- package/dist/units/index.d.ts.map +1 -0
- package/dist/units/index.js +22 -0
- package/dist/units/index.js.map +1 -0
- package/dist/units/unit-parser.d.ts +19 -0
- package/dist/units/unit-parser.d.ts.map +1 -0
- package/dist/units/unit-parser.js +53 -0
- package/dist/units/unit-parser.js.map +1 -0
- package/dist/units/units.d.ts +37 -0
- package/dist/units/units.d.ts.map +1 -0
- package/dist/units/units.js +36 -0
- package/dist/units/units.js.map +1 -0
- package/package.json +89 -0
- package/src/_embedder/base.ts +42 -0
- package/src/_embedder/index.ts +1 -0
- package/src/_string/index.ts +5 -0
- package/src/_string/markers.ts +47 -0
- package/src/_string/post-processor.ts +25 -0
- package/src/_string/pretty-objects.ts +65 -0
- package/src/_string/pretty-print.ts +24 -0
- package/src/_string/super-script.ts +17 -0
- package/src/api-kind/index.ts +134 -0
- package/src/cmd/cli-command.ts +89 -0
- package/src/cmd/cli-term.ts +60 -0
- package/src/cmd/index.ts +2 -0
- package/src/cmd/types.ts +4 -0
- package/src/displayers/displayers.ts +147 -0
- package/src/displayers/index.ts +1 -0
- package/src/env/env.ts +74 -0
- package/src/env/index.ts +2 -0
- package/src/env/types.ts +7 -0
- package/src/env/validate-name.ts +10 -0
- package/src/error.ts +15 -0
- package/src/forward-exports/delayed-exports.ts +155 -0
- package/src/forward-exports/index.ts +1 -0
- package/src/graph/base-node.ts +125 -0
- package/src/graph/base-origin-entity.ts +44 -0
- package/src/graph/dependencies.ts +27 -0
- package/src/graph/index.ts +6 -0
- package/src/graph/origin-node.ts +118 -0
- package/src/graph/relations.ts +62 -0
- package/src/graph/resource-node.ts +104 -0
- package/src/image/family.ts +71 -0
- package/src/image/index.ts +1 -0
- package/src/index.ts +18 -0
- package/src/kind-map/index.ts +150 -0
- package/src/manifest/index.ts +53 -0
- package/src/manifest/manifest-builder.ts +98 -0
- package/src/ports/error.ts +8 -0
- package/src/ports/index.ts +8 -0
- package/src/ports/map.ts +41 -0
- package/src/ports/set.ts +79 -0
- package/src/ports/tools/entry.ts +43 -0
- package/src/ports/tools/parse.ts +40 -0
- package/src/ports/types.ts +42 -0
- package/src/producer/index.ts +1 -0
- package/src/producer/producer.ts +18 -0
- package/src/ref-key/index.ts +1 -0
- package/src/ref-key/ref-key.ts +76 -0
- package/src/reference/forward-ref.ts +122 -0
- package/src/reference/index.ts +3 -0
- package/src/reference/refable.ts +11 -0
- package/src/resources/index.ts +2 -0
- package/src/resources/objects.ts +99 -0
- package/src/resources/parser.ts +24 -0
- package/src/resources/types.ts +23 -0
- package/src/tracing/git.ts +51 -0
- package/src/tracing/index.ts +3 -0
- package/src/tracing/trace.ts +31 -0
- package/src/tracing/traced.ts +4 -0
- package/src/tsconfig.json +10 -0
- package/src/units/index.ts +2 -0
- package/src/units/unit-parser.ts +63 -0
- package/src/units/units.ts +53 -0
- package/tsconfig.json +15 -0
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
import { seq } from "doddle"
|
|
2
|
+
import { ProxyOperationError } from "../error"
|
|
3
|
+
import { Origin } from "../graph/origin-node"
|
|
4
|
+
import type { LiveRefable } from "../reference"
|
|
5
|
+
import { ForwardRef } from "../reference"
|
|
6
|
+
|
|
7
|
+
export type FutureExports<Exps extends LiveRefable> = FutureExports.FutureExports<Exps>
|
|
8
|
+
export namespace FutureExports {
|
|
9
|
+
export type FutureExports<Exps extends LiveRefable> = _ExportsByKey<Exps>
|
|
10
|
+
type _ExportsByKey<Exports extends LiveRefable = LiveRefable> = {
|
|
11
|
+
[E in Exports as `${E["kind"]["name"]}/${E["node"]["key"]["name"]}`]: ForwardRef<E>
|
|
12
|
+
}
|
|
13
|
+
export interface Props<
|
|
14
|
+
Actual extends object = object,
|
|
15
|
+
Exports extends LiveRefable = LiveRefable
|
|
16
|
+
> {
|
|
17
|
+
readonly origin: Origin
|
|
18
|
+
readonly actual: Actual
|
|
19
|
+
readonly exports: Iterable<Exports>
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
export function make<T extends LiveRefable, Actual extends object>(
|
|
23
|
+
props: Props<Actual, T>
|
|
24
|
+
): Actual & FutureExports<LiveRefable> {
|
|
25
|
+
const handler = new Handler(props)
|
|
26
|
+
return new Proxy(props.actual, handler) as any
|
|
27
|
+
}
|
|
28
|
+
class Handler implements ProxyHandler<object> {
|
|
29
|
+
constructor(private readonly _props: Props) {}
|
|
30
|
+
|
|
31
|
+
#createImmutableError(action: string) {
|
|
32
|
+
return new ProxyOperationError(
|
|
33
|
+
`Tried to ${action} an the exports constructs of ${this._props.origin}, but it is immutable.`
|
|
34
|
+
)
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
defineProperty(_: object, property: string | symbol, __: PropertyDescriptor): boolean {
|
|
38
|
+
throw this.#createImmutableError(`define property ${String(property)} on`)
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
deleteProperty(_: object, property: string | symbol): boolean {
|
|
42
|
+
throw this.#createImmutableError(`delete property ${String(property)} from`)
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
getPrototypeOf(_: Iterable<LiveRefable>): object | null {
|
|
46
|
+
return Reflect.getPrototypeOf(this._target)
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
get seq() {
|
|
50
|
+
return seq(this._props.exports)
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
#isValidReferant(prop: PropertyKey) {
|
|
54
|
+
return this._props.origin.resourceKinds.tryParse(prop as string) != null
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
get _target() {
|
|
58
|
+
return this._props.actual
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
get(target: any, property: string | symbol): any {
|
|
62
|
+
const key = property as string
|
|
63
|
+
if (Reflect.has(this._target, key)) {
|
|
64
|
+
const x = Reflect.get(this._target, property)
|
|
65
|
+
if (typeof x === "function") {
|
|
66
|
+
return x.bind(this._target)
|
|
67
|
+
}
|
|
68
|
+
return x
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
const refKey = this._props.origin.resourceKinds.tryParse(key)
|
|
72
|
+
if (refKey == null) {
|
|
73
|
+
return undefined
|
|
74
|
+
}
|
|
75
|
+
const cls = this._props.origin.resourceKinds.getClass(refKey)
|
|
76
|
+
return ForwardRef.make({
|
|
77
|
+
class: cls,
|
|
78
|
+
key: refKey,
|
|
79
|
+
origin: this._props.origin,
|
|
80
|
+
namespace: this._props.origin.meta.tryGet("namespace"),
|
|
81
|
+
resolver: this.seq
|
|
82
|
+
.find(exp => exp.node.key.equals(refKey))
|
|
83
|
+
.map(x => {
|
|
84
|
+
if (x == null) {
|
|
85
|
+
throw new ProxyOperationError(
|
|
86
|
+
`Failed to resolve forward reference to ${refKey} in ${this._props.origin}.`
|
|
87
|
+
)
|
|
88
|
+
}
|
|
89
|
+
return x
|
|
90
|
+
})
|
|
91
|
+
})
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
has(_: Iterable<LiveRefable>, p: string | symbol): boolean {
|
|
95
|
+
if (Reflect.has(this._target, p)) {
|
|
96
|
+
return true
|
|
97
|
+
}
|
|
98
|
+
if (!this.#isValidReferant(p)) {
|
|
99
|
+
return false
|
|
100
|
+
}
|
|
101
|
+
return true
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
isExtensible(target: Iterable<LiveRefable>): boolean {
|
|
105
|
+
return false
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
preventExtensions(target: Iterable<LiveRefable>): boolean {
|
|
109
|
+
return true
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
ownKeys(target: Iterable<LiveRefable>): ArrayLike<string | symbol> {
|
|
113
|
+
throw new ProxyOperationError(
|
|
114
|
+
`Cannot list all keys of a dynamic exports construct for ${this._props.origin}.`
|
|
115
|
+
)
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
set(
|
|
119
|
+
target: Iterable<LiveRefable>,
|
|
120
|
+
p: string | symbol,
|
|
121
|
+
newValue: any,
|
|
122
|
+
receiver: any
|
|
123
|
+
): boolean {
|
|
124
|
+
throw this.#createImmutableError(`set property ${String(p)} on`)
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
setPrototypeOf(target: Iterable<LiveRefable>, v: any): boolean {
|
|
128
|
+
throw this.#createImmutableError(`set prototype of`)
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
_tryTargetDescriptor(p: PropertyKey) {
|
|
132
|
+
return Object.getOwnPropertyDescriptor(this._target, p)
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
getOwnPropertyDescriptor(
|
|
136
|
+
target: Iterable<LiveRefable>,
|
|
137
|
+
p: string | symbol
|
|
138
|
+
): PropertyDescriptor | undefined {
|
|
139
|
+
const desc = this._tryTargetDescriptor(p)
|
|
140
|
+
if (desc) {
|
|
141
|
+
return desc
|
|
142
|
+
}
|
|
143
|
+
const value = this.get(this._target, p)
|
|
144
|
+
if (value == null) {
|
|
145
|
+
return undefined
|
|
146
|
+
}
|
|
147
|
+
return {
|
|
148
|
+
configurable: false,
|
|
149
|
+
enumerable: true,
|
|
150
|
+
value,
|
|
151
|
+
writable: false
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from "./delayed-exports"
|
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
import { Seq, seq } from "doddle"
|
|
2
|
+
import { hash, Set } from "immutable"
|
|
3
|
+
import { Kind } from "../api-kind"
|
|
4
|
+
import { RefKey } from "../ref-key"
|
|
5
|
+
import { ForwardRef } from "../reference"
|
|
6
|
+
import { NeedsEdge } from "./dependencies"
|
|
7
|
+
|
|
8
|
+
export interface BaseEntity<Node extends BaseNode<Node>> {
|
|
9
|
+
readonly node: Node
|
|
10
|
+
|
|
11
|
+
readonly shortFqn: string
|
|
12
|
+
readonly kind: Kind.Identifier
|
|
13
|
+
readonly name: string
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
export abstract class BaseNode<
|
|
17
|
+
Node extends BaseNode<Node, Entity>,
|
|
18
|
+
Entity extends BaseEntity<Node> = BaseEntity<Node>
|
|
19
|
+
> {
|
|
20
|
+
abstract readonly key: RefKey
|
|
21
|
+
get kind() {
|
|
22
|
+
return this.key.kind
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
abstract readonly kids: Seq<Node>
|
|
26
|
+
abstract readonly needs: Seq<NeedsEdge<Node>>
|
|
27
|
+
abstract readonly parent: Node | null
|
|
28
|
+
protected get _asNode() {
|
|
29
|
+
return this as any as Node
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
constructor(readonly _entity: Entity) {}
|
|
33
|
+
|
|
34
|
+
get shortFqn() {
|
|
35
|
+
return `${this.kind.name}/${this.name}`
|
|
36
|
+
}
|
|
37
|
+
get root(): Node {
|
|
38
|
+
return (this.ancestors.at(-1).pull() as any) ?? (this as any)
|
|
39
|
+
}
|
|
40
|
+
get name() {
|
|
41
|
+
return this.key.name
|
|
42
|
+
}
|
|
43
|
+
get isRoot() {
|
|
44
|
+
return this.parent === null
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
hashCode() {
|
|
48
|
+
return hash(this)
|
|
49
|
+
}
|
|
50
|
+
equals(other: any) {
|
|
51
|
+
if (ForwardRef.is(other)) {
|
|
52
|
+
return other.equals(this)
|
|
53
|
+
}
|
|
54
|
+
return this === other
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
readonly ancestors = seq(() => {
|
|
58
|
+
const seen = Set<Node>()
|
|
59
|
+
const recurse = function* (from: Node): Iterable<Node> {
|
|
60
|
+
const parent = from.parent
|
|
61
|
+
if (parent && !seen.has(parent)) {
|
|
62
|
+
seen.add(parent)
|
|
63
|
+
yield parent
|
|
64
|
+
yield* recurse(parent)
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
return seq(recurse.bind(null, this._asNode))
|
|
68
|
+
}).cache()
|
|
69
|
+
|
|
70
|
+
readonly descendants = seq(() => {
|
|
71
|
+
const self = this
|
|
72
|
+
let seen = Set<Node>()
|
|
73
|
+
const recurse = function* (from: Node): Iterable<Node> {
|
|
74
|
+
for (const kid of from.kids) {
|
|
75
|
+
if (seen.has(kid)) {
|
|
76
|
+
continue
|
|
77
|
+
}
|
|
78
|
+
seen = seen.add(kid)
|
|
79
|
+
yield kid
|
|
80
|
+
yield* recurse(kid)
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
return seq(recurse.bind(null, self._asNode))
|
|
84
|
+
}).cache()
|
|
85
|
+
|
|
86
|
+
isParentOf(other: Node): boolean {
|
|
87
|
+
if (ForwardRef.is(other)) {
|
|
88
|
+
return other.isChildOf(this._asNode)
|
|
89
|
+
}
|
|
90
|
+
return Set(this.descendants).has(other)
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
isChildOf(other: Node): boolean {
|
|
94
|
+
if (ForwardRef.is(other)) {
|
|
95
|
+
return other.isParentOf(this._asNode)
|
|
96
|
+
}
|
|
97
|
+
return this.equals(other) || Set(this.ancestors).has(other._asNode)
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
isNeeding(other: Node): boolean {
|
|
101
|
+
return this.needsGraph.some(x => x.needed.equals(other)).pull()
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
readonly needsGraph = seq(() => {
|
|
105
|
+
let resources = Set<Node>()
|
|
106
|
+
const recurseIntoDependency = function* (root: NeedsEdge<Node>): Iterable<NeedsEdge<Node>> {
|
|
107
|
+
yield root
|
|
108
|
+
if (resources.has(root.needed)) {
|
|
109
|
+
return
|
|
110
|
+
}
|
|
111
|
+
resources = resources.add(root.needed)
|
|
112
|
+
|
|
113
|
+
const ownDeps = root.needed.needs
|
|
114
|
+
for (const needsEdge of ownDeps) {
|
|
115
|
+
yield* recurseIntoDependency(needsEdge)
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
return seq(recurseIntoDependency.bind(null, new NeedsEdge<Node>("self", this._asNode)))
|
|
119
|
+
.after(() => {
|
|
120
|
+
resources = Set()
|
|
121
|
+
})
|
|
122
|
+
.cache()
|
|
123
|
+
})
|
|
124
|
+
}
|
|
125
|
+
export type Formats = "short" | "fqn" | "shortFqn"
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import { Meta } from "@k8ts/metadata"
|
|
2
|
+
import chalk from "chalk"
|
|
3
|
+
import { doddle, Doddle } from "doddle"
|
|
4
|
+
import { Kind } from "../api-kind"
|
|
5
|
+
import { displayers } from "../displayers"
|
|
6
|
+
import { RefKey } from "../ref-key"
|
|
7
|
+
import { Origin, OriginEntity } from "./origin-node"
|
|
8
|
+
export interface OriginEntityProps {
|
|
9
|
+
meta?: Meta.Input
|
|
10
|
+
alias?: string
|
|
11
|
+
}
|
|
12
|
+
@displayers({
|
|
13
|
+
simple: x => `[${x.shortFqn}]`,
|
|
14
|
+
pretty(origin) {
|
|
15
|
+
const kindPart = chalk.greenBright.bold(origin.kind.name)
|
|
16
|
+
const originName = chalk.cyan(origin.name)
|
|
17
|
+
return `${kindPart}/${originName}`
|
|
18
|
+
}
|
|
19
|
+
})
|
|
20
|
+
export abstract class BaseOriginEntity<Props extends OriginEntityProps = OriginEntityProps>
|
|
21
|
+
implements OriginEntity
|
|
22
|
+
{
|
|
23
|
+
abstract readonly kind: Kind.Kind
|
|
24
|
+
#node: Doddle<Origin>
|
|
25
|
+
|
|
26
|
+
meta: Meta
|
|
27
|
+
get alias() {
|
|
28
|
+
return this.props.alias ?? undefined
|
|
29
|
+
}
|
|
30
|
+
get node() {
|
|
31
|
+
return this.#node.pull()
|
|
32
|
+
}
|
|
33
|
+
constructor(
|
|
34
|
+
readonly name: string,
|
|
35
|
+
readonly props: Props,
|
|
36
|
+
parent: Origin | null
|
|
37
|
+
) {
|
|
38
|
+
this.#node = doddle(() => new Origin(parent, this, RefKey.make(this.kind, name)))
|
|
39
|
+
this.meta = Meta.make(props.meta)
|
|
40
|
+
}
|
|
41
|
+
get shortFqn() {
|
|
42
|
+
return this.node.shortFqn
|
|
43
|
+
}
|
|
44
|
+
}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import chalk from "chalk"
|
|
2
|
+
import { pretty } from "../_string"
|
|
3
|
+
import { displayers } from "../displayers"
|
|
4
|
+
import { BaseNode } from "./base-node"
|
|
5
|
+
import { ResourceEntity } from "./resource-node"
|
|
6
|
+
|
|
7
|
+
export namespace Dependencies {
|
|
8
|
+
export type Input = Record<string, ResourceEntity>
|
|
9
|
+
}
|
|
10
|
+
export function dependencies(record: Dependencies.Input) {
|
|
11
|
+
return Object.entries(record).map(([key, value]) => {
|
|
12
|
+
return new NeedsEdge(key, value.node)
|
|
13
|
+
})
|
|
14
|
+
}
|
|
15
|
+
@displayers({
|
|
16
|
+
simple: s => [s.why, "-->", s.needed],
|
|
17
|
+
pretty: (dep, format) => {
|
|
18
|
+
const neededFmt = pretty`${["lowkey", dep.needed]}`
|
|
19
|
+
return [`${chalk.gray.italic.white(`${dep.why}`)}`, "➜ ", chalk.italic(`${neededFmt}`)]
|
|
20
|
+
}
|
|
21
|
+
})
|
|
22
|
+
export class NeedsEdge<Node extends BaseNode<Node>> {
|
|
23
|
+
constructor(
|
|
24
|
+
readonly why: string,
|
|
25
|
+
readonly needed: Node
|
|
26
|
+
) {}
|
|
27
|
+
}
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
import { Meta } from "@k8ts/metadata"
|
|
2
|
+
import chalk from "chalk"
|
|
3
|
+
import { doddle, seq, Seq } from "doddle"
|
|
4
|
+
import StackTracey from "stacktracey"
|
|
5
|
+
import { getMarkerForIndex, toSuperScript } from "../_string"
|
|
6
|
+
import { displayers } from "../displayers"
|
|
7
|
+
import { KindMap } from "../kind-map"
|
|
8
|
+
import { RefKey } from "../ref-key"
|
|
9
|
+
import { TraceEmbedder } from "../tracing"
|
|
10
|
+
import { Trace } from "../tracing/trace"
|
|
11
|
+
import { BaseEntity, BaseNode } from "./base-node"
|
|
12
|
+
import { ResourceNode } from "./resource-node"
|
|
13
|
+
@displayers({
|
|
14
|
+
simple: s => `[${s.shortFqn}]`,
|
|
15
|
+
prefix: s => {
|
|
16
|
+
if (s.name === "EXTERNAL") {
|
|
17
|
+
return "🌐"
|
|
18
|
+
}
|
|
19
|
+
return getMarkerForIndex(s.index, s._entity.alias ?? toSuperScript(s.index))
|
|
20
|
+
},
|
|
21
|
+
pretty(origin, format) {
|
|
22
|
+
const kindName = chalk.greenBright.bold(origin.kind.name)
|
|
23
|
+
const resourceName = chalk.cyan(origin.name)
|
|
24
|
+
const pref = this.prefix!()
|
|
25
|
+
|
|
26
|
+
return `${kindName}:${resourceName} (${pref})`
|
|
27
|
+
}
|
|
28
|
+
})
|
|
29
|
+
export class Origin extends BaseNode<Origin, OriginEntity> implements Iterable<ResourceNode> {
|
|
30
|
+
private _kids = [] as Origin[]
|
|
31
|
+
get kids() {
|
|
32
|
+
return seq(this._kids)
|
|
33
|
+
}
|
|
34
|
+
get meta() {
|
|
35
|
+
return this._entity.meta
|
|
36
|
+
}
|
|
37
|
+
readonly index: number
|
|
38
|
+
private readonly _getIndex = doddle(() => {
|
|
39
|
+
let index = 1
|
|
40
|
+
return () => index++
|
|
41
|
+
}).pull()
|
|
42
|
+
constructor(
|
|
43
|
+
readonly parent: Origin | null,
|
|
44
|
+
entity: OriginEntity,
|
|
45
|
+
readonly key: RefKey
|
|
46
|
+
) {
|
|
47
|
+
super(entity)
|
|
48
|
+
this.index = parent?._getIndex() ?? 0
|
|
49
|
+
this._kindMap = new KindMap(undefined, parent?._kindMap)
|
|
50
|
+
}
|
|
51
|
+
get resourceKinds() {
|
|
52
|
+
return this._kindMap
|
|
53
|
+
}
|
|
54
|
+
private _kindMap: KindMap
|
|
55
|
+
private _attached = [] as ResourceNode[]
|
|
56
|
+
|
|
57
|
+
get needs() {
|
|
58
|
+
return seq.empty()
|
|
59
|
+
}
|
|
60
|
+
[Symbol.iterator]() {
|
|
61
|
+
return this.resources[Symbol.iterator]()
|
|
62
|
+
}
|
|
63
|
+
readonly attachedTree: Seq<ResourceNode> = seq(() => {
|
|
64
|
+
const self = this
|
|
65
|
+
const desc = self.descendants.prepend(this).concatMap(function* (x) {
|
|
66
|
+
yield* self.resources
|
|
67
|
+
for (const kid of self.kids) {
|
|
68
|
+
yield* kid.resources
|
|
69
|
+
}
|
|
70
|
+
})
|
|
71
|
+
return desc
|
|
72
|
+
}).cache()
|
|
73
|
+
|
|
74
|
+
get resources() {
|
|
75
|
+
return this._attached
|
|
76
|
+
}
|
|
77
|
+
static registerWithOrigin<F extends Function>(ctor: F) {
|
|
78
|
+
const prototype = ctor.prototype
|
|
79
|
+
for (const key of Object.getOwnPropertyNames(prototype)) {
|
|
80
|
+
const value = prototype[key]
|
|
81
|
+
if (!key.match(/^[A-Z]/) || typeof value !== "function") {
|
|
82
|
+
continue
|
|
83
|
+
}
|
|
84
|
+
const orig = prototype[key]
|
|
85
|
+
prototype[key] = {
|
|
86
|
+
[key](this: any, ...args: any[]) {
|
|
87
|
+
const result = orig.apply(this, args) as BaseEntity<any>
|
|
88
|
+
if (
|
|
89
|
+
typeof result === "object" &&
|
|
90
|
+
"node" in result &&
|
|
91
|
+
result.node instanceof ResourceNode
|
|
92
|
+
) {
|
|
93
|
+
result.node.origin.__attach_resource__([result.node])
|
|
94
|
+
TraceEmbedder.set(result.node, new Trace(new StackTracey().slice(1)))
|
|
95
|
+
}
|
|
96
|
+
return result
|
|
97
|
+
}
|
|
98
|
+
}[key]
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
private __attach_child__(child: Origin) {
|
|
103
|
+
this._kids.push(child)
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
private __attach_resource__(resources: ResourceNode | Iterable<ResourceNode>) {
|
|
107
|
+
resources = Symbol.iterator in resources ? resources : [resources]
|
|
108
|
+
for (const resource of resources) {
|
|
109
|
+
this._attached.push(resource)
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
export interface OriginEntity extends BaseEntity<Origin> {
|
|
114
|
+
alias?: string
|
|
115
|
+
meta: Meta
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
export const auto_register = Origin.registerWithOrigin
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
import { Embedder } from "../_embedder/base"
|
|
2
|
+
import { Dependencies, dependencies, NeedsEdge } from "./dependencies"
|
|
3
|
+
import { ResourceEntity, ResourceNode } from "./resource-node"
|
|
4
|
+
|
|
5
|
+
export namespace Relations {
|
|
6
|
+
export interface Out {
|
|
7
|
+
needs: () => Iterable<NeedsEdge<ResourceNode>>
|
|
8
|
+
parent: () => ResourceNode | null
|
|
9
|
+
kids: () => ResourceNode[]
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
export type In<Target extends ResourceEntity = ResourceEntity> = {
|
|
13
|
+
needs: (self: Target) => Dependencies.Input
|
|
14
|
+
parent: (self: Target) => ResourceEntity | null
|
|
15
|
+
kids: (self: Target) => ResourceEntity[]
|
|
16
|
+
} & {
|
|
17
|
+
[key: string]: (self: Target, ...args: any[]) => any
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
class RelationsService {
|
|
22
|
+
private _system = new Embedder<ResourceEntity, Relations.In>("relations")
|
|
23
|
+
|
|
24
|
+
implement(
|
|
25
|
+
ctor: abstract new (...args: any[]) => ResourceEntity,
|
|
26
|
+
input: Relations.In<ResourceEntity>
|
|
27
|
+
) {
|
|
28
|
+
const existing = this._system.tryGet(ctor.prototype)
|
|
29
|
+
if (existing) {
|
|
30
|
+
input = Object.assign({}, existing, input)
|
|
31
|
+
}
|
|
32
|
+
this._system.set(ctor.prototype, input)
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
get(target: ResourceEntity): Relations.Out {
|
|
36
|
+
const input = this._system.get(target)
|
|
37
|
+
const o = {
|
|
38
|
+
kids: () => input.kids?.call(o, target).map(x => x.node) ?? [],
|
|
39
|
+
parent: () => input.parent?.call(o, target)?.node ?? null,
|
|
40
|
+
needs: () => dependencies(input.needs?.call(o, target) ?? {})
|
|
41
|
+
}
|
|
42
|
+
return o
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
get decorator() {
|
|
46
|
+
return <
|
|
47
|
+
Target extends abstract new (...args: any[]) => ResourceEntity,
|
|
48
|
+
Impl extends Partial<Relations.In<InstanceType<Target>>> | "none"
|
|
49
|
+
>(
|
|
50
|
+
input: Impl
|
|
51
|
+
) => {
|
|
52
|
+
return (ctor: Target) => {
|
|
53
|
+
this.implement(ctor, input === "none" ? {} : (input as any))
|
|
54
|
+
return ctor
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
export const Relations = new RelationsService()
|
|
60
|
+
export const relations = Relations.decorator
|
|
61
|
+
|
|
62
|
+
// writing the decorator itself
|
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
import { MutableMeta } from "@k8ts/metadata"
|
|
2
|
+
import chalk from "chalk"
|
|
3
|
+
import { seq } from "doddle"
|
|
4
|
+
import { displayers } from "../displayers"
|
|
5
|
+
import { RefKey } from "../ref-key"
|
|
6
|
+
import { TraceEmbedder } from "../tracing"
|
|
7
|
+
import { BaseEntity, BaseNode, Formats } from "./base-node"
|
|
8
|
+
import { Origin } from "./origin-node"
|
|
9
|
+
import { Relations } from "./relations"
|
|
10
|
+
|
|
11
|
+
@displayers({
|
|
12
|
+
simple: s => `[${s.shortFqn}]`,
|
|
13
|
+
pretty(resource, format) {
|
|
14
|
+
format ??= "global"
|
|
15
|
+
|
|
16
|
+
let kindName = chalk.greenBright(resource.kind.name)
|
|
17
|
+
if (format !== "lowkey") {
|
|
18
|
+
kindName = chalk.bold(kindName)
|
|
19
|
+
}
|
|
20
|
+
const resourceName = chalk.blueBright(resource.name)
|
|
21
|
+
const mainPart = `${kindName}/${resourceName}`
|
|
22
|
+
let originPart = ` (${displayers.get(resource.origin).prefix!()})`
|
|
23
|
+
let text = ""
|
|
24
|
+
|
|
25
|
+
text += mainPart
|
|
26
|
+
if (format !== "local") {
|
|
27
|
+
text += originPart
|
|
28
|
+
}
|
|
29
|
+
return text
|
|
30
|
+
}
|
|
31
|
+
})
|
|
32
|
+
export class ResourceNode extends BaseNode<ResourceNode, ResourceEntity> {
|
|
33
|
+
get needs() {
|
|
34
|
+
return seq(this._relations.needs)
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
get trace() {
|
|
38
|
+
return TraceEmbedder.get(this)
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
get isExported() {
|
|
42
|
+
return this.meta?.tryGet("#k8ts.org/is-exported") ?? false
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
get meta() {
|
|
46
|
+
return "meta" in this._entity ? (this._entity.meta as MutableMeta) : undefined
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
get isExternal() {
|
|
50
|
+
return this.origins.some(x => x.name === "EXTERNAL").pull()
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
get origins() {
|
|
54
|
+
const self = this
|
|
55
|
+
return seq(function* () {
|
|
56
|
+
let current: Origin | null = self.origin
|
|
57
|
+
while (current) {
|
|
58
|
+
yield current
|
|
59
|
+
current = current.parent
|
|
60
|
+
}
|
|
61
|
+
})
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
get kids() {
|
|
65
|
+
return seq(this._relations.kids)
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
get parent() {
|
|
69
|
+
return this._relations.parent()
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
override get shortFqn() {
|
|
73
|
+
return `${this.origin.name}:${this.key}`
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
get localName() {
|
|
77
|
+
return this.key.string
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
format(format: Formats) {
|
|
81
|
+
switch (format) {
|
|
82
|
+
case "short":
|
|
83
|
+
return this.name
|
|
84
|
+
case "fqn":
|
|
85
|
+
return this.key.string
|
|
86
|
+
case "shortFqn":
|
|
87
|
+
return this.key.name
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
private get _relations() {
|
|
91
|
+
return Relations.get(this._entity)
|
|
92
|
+
}
|
|
93
|
+
constructor(
|
|
94
|
+
readonly origin: Origin,
|
|
95
|
+
readonly entity: ResourceEntity,
|
|
96
|
+
readonly key: RefKey
|
|
97
|
+
) {
|
|
98
|
+
super(entity)
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
export interface MetadataEntity extends BaseEntity<ResourceNode> {
|
|
102
|
+
meta: MutableMeta
|
|
103
|
+
}
|
|
104
|
+
export interface ResourceEntity extends BaseEntity<ResourceNode> {}
|