@likec4/core 1.12.2 → 1.13.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/dist/index.cjs +777 -251
- package/dist/index.d.cts +301 -32
- package/dist/index.d.mts +301 -32
- package/dist/index.d.ts +301 -32
- package/dist/index.mjs +774 -252
- package/dist/shared/{core.BvFch1jG.mjs → core.BJDxVHFh.mjs} +19 -19
- package/dist/shared/{core.dY8efyk0.d.ts → core.C4jDMQ1i.d.cts} +242 -238
- package/dist/shared/{core.dY8efyk0.d.cts → core.C4jDMQ1i.d.mts} +242 -238
- package/dist/shared/{core.dY8efyk0.d.mts → core.C4jDMQ1i.d.ts} +242 -238
- package/dist/shared/{core.CTiE4teS.cjs → core.IR7XOEkQ.cjs} +19 -18
- package/dist/types/index.cjs +1 -1
- package/dist/types/index.d.cts +1 -1
- package/dist/types/index.d.mts +1 -1
- package/dist/types/index.d.ts +1 -1
- package/dist/types/index.mjs +1 -1
- package/package.json +4 -3
- package/src/builder/Builder.element.ts +221 -0
- package/src/builder/Builder.model.ts +346 -0
- package/src/builder/Builder.test-d.ts +69 -0
- package/src/builder/Builder.ts +574 -0
- package/src/builder/Builder.view.ts +358 -0
- package/src/builder/Builder.views.ts +318 -0
- package/src/builder/_types.ts +195 -0
- package/src/builder/index.ts +5 -0
- package/src/index.ts +4 -0
- package/src/model/LikeC4DiagramModel.ts +5 -5
- package/src/model/LikeC4Model.ts +63 -46
- package/src/model/LikeC4ViewModel.ts +7 -7
- package/src/model/__test__/fixture.ts +5 -0
- package/src/types/element.ts +19 -11
- package/src/types/model.ts +13 -8
- package/src/types/relation.ts +1 -1
- package/src/types/view-changes.ts +6 -2
- package/src/types/view.ts +53 -22
- package/src/utils/fqn.ts +12 -11
package/src/types/view.ts
CHANGED
|
@@ -7,8 +7,7 @@ import type { RelationID, RelationshipArrowType, RelationshipKind, RelationshipL
|
|
|
7
7
|
import type { Color, ThemeColorValues } from './theme'
|
|
8
8
|
import type { ElementNotation } from './view-notation'
|
|
9
9
|
|
|
10
|
-
|
|
11
|
-
export type ViewID = Tagged<string, 'ViewID'>
|
|
10
|
+
export type ViewID<Id extends string = string> = Tagged<Id, 'ViewID'>
|
|
12
11
|
|
|
13
12
|
export type ViewRulePredicate =
|
|
14
13
|
| {
|
|
@@ -55,12 +54,16 @@ export function isViewRuleAutoLayout(rule: ViewRule): rule is ViewRuleAutoLayout
|
|
|
55
54
|
|
|
56
55
|
export type ViewRule = ViewRulePredicate | ViewRuleStyle | ViewRuleAutoLayout
|
|
57
56
|
|
|
58
|
-
export interface BasicView<
|
|
57
|
+
export interface BasicView<
|
|
58
|
+
ViewType extends 'element' | 'dynamic',
|
|
59
|
+
ViewIDs extends string,
|
|
60
|
+
Tags extends string
|
|
61
|
+
> {
|
|
59
62
|
readonly __?: ViewType
|
|
60
|
-
readonly id: ViewID
|
|
63
|
+
readonly id: ViewID<ViewIDs>
|
|
61
64
|
readonly title: string | null
|
|
62
65
|
readonly description: string | null
|
|
63
|
-
readonly tags: NonEmptyArray<Tag
|
|
66
|
+
readonly tags: NonEmptyArray<Tag<Tags>> | null
|
|
64
67
|
readonly links: NonEmptyArray<Link> | null
|
|
65
68
|
|
|
66
69
|
/**
|
|
@@ -86,18 +89,30 @@ export interface BasicView<ViewType extends 'element' | 'dynamic'> {
|
|
|
86
89
|
readonly customColorDefinitions: CustomColorDefinitions
|
|
87
90
|
}
|
|
88
91
|
|
|
89
|
-
export interface BasicElementView extends
|
|
92
|
+
export interface BasicElementView<ViewIDs extends string, Tags extends string>
|
|
93
|
+
extends BasicView<'element', ViewIDs, Tags>
|
|
94
|
+
{
|
|
90
95
|
readonly viewOf?: Fqn
|
|
91
96
|
readonly rules: ViewRule[]
|
|
92
97
|
}
|
|
93
|
-
export interface ScopedElementView extends
|
|
98
|
+
export interface ScopedElementView<ViewIDs extends string, Tags extends string>
|
|
99
|
+
extends BasicElementView<ViewIDs, Tags>
|
|
100
|
+
{
|
|
94
101
|
readonly viewOf: Fqn
|
|
95
102
|
}
|
|
96
103
|
|
|
97
|
-
export interface ExtendsElementView extends
|
|
98
|
-
|
|
104
|
+
export interface ExtendsElementView<ViewIDs extends string, Tags extends string>
|
|
105
|
+
extends BasicElementView<ViewIDs, Tags>
|
|
106
|
+
{
|
|
107
|
+
readonly extends: ViewID<ViewIDs>
|
|
99
108
|
}
|
|
100
|
-
export type ElementView
|
|
109
|
+
export type ElementView<
|
|
110
|
+
ViewIDs extends string = string,
|
|
111
|
+
Tags extends string = string
|
|
112
|
+
> =
|
|
113
|
+
| ScopedElementView<ViewIDs, Tags>
|
|
114
|
+
| ExtendsElementView<ViewIDs, Tags>
|
|
115
|
+
| BasicElementView<ViewIDs, Tags>
|
|
101
116
|
|
|
102
117
|
export interface DynamicViewStep {
|
|
103
118
|
readonly source: Fqn
|
|
@@ -133,7 +148,10 @@ export function isDynamicViewIncludeRule(rule: DynamicViewRule): rule is Dynamic
|
|
|
133
148
|
}
|
|
134
149
|
|
|
135
150
|
export type DynamicViewRule = DynamicViewIncludeRule | ViewRuleStyle | ViewRuleAutoLayout
|
|
136
|
-
export interface DynamicView
|
|
151
|
+
export interface DynamicView<
|
|
152
|
+
ViewIDs extends string = string,
|
|
153
|
+
Tags extends string = string
|
|
154
|
+
> extends BasicView<'dynamic', ViewIDs, Tags> {
|
|
137
155
|
readonly __: 'dynamic'
|
|
138
156
|
|
|
139
157
|
readonly steps: DynamicViewStepOrParallel[]
|
|
@@ -147,7 +165,10 @@ export function isDynamicViewParallelSteps(step: DynamicViewStepOrParallel): ste
|
|
|
147
165
|
|
|
148
166
|
export type CustomColorDefinitions = { [key: string]: ThemeColorValues }
|
|
149
167
|
|
|
150
|
-
export type LikeC4View
|
|
168
|
+
export type LikeC4View<
|
|
169
|
+
ViewIDs extends string = string,
|
|
170
|
+
Tags extends string = string
|
|
171
|
+
> = ElementView<ViewIDs, Tags> | DynamicView<ViewIDs, Tags>
|
|
151
172
|
|
|
152
173
|
export function isDynamicView(view: LikeC4View): view is DynamicView {
|
|
153
174
|
return view.__ === 'dynamic'
|
|
@@ -156,15 +177,15 @@ export function isElementView(view: LikeC4View): view is ElementView {
|
|
|
156
177
|
return isNullish(view.__) || view.__ === 'element'
|
|
157
178
|
}
|
|
158
179
|
|
|
159
|
-
export function isExtendsElementView(view: LikeC4View): view is ExtendsElementView {
|
|
180
|
+
export function isExtendsElementView(view: LikeC4View): view is ExtendsElementView<string, string> {
|
|
160
181
|
return isElementView(view) && 'extends' in view
|
|
161
182
|
}
|
|
162
183
|
|
|
163
|
-
export function isScopedElementView(view: LikeC4View): view is ScopedElementView {
|
|
184
|
+
export function isScopedElementView(view: LikeC4View): view is ScopedElementView<string, string> {
|
|
164
185
|
return isElementView(view) && 'viewOf' in view
|
|
165
186
|
}
|
|
166
187
|
|
|
167
|
-
export type NodeId = Tagged<
|
|
188
|
+
export type NodeId<IDs extends string = string> = Tagged<IDs, 'Fqn'>
|
|
168
189
|
|
|
169
190
|
export type EdgeId = Tagged<string, 'EdgeId'>
|
|
170
191
|
export type StepEdgeIdLiteral = `step-${number}` | `step-${number}.${number}`
|
|
@@ -276,17 +297,21 @@ export interface ViewAutoLayout {
|
|
|
276
297
|
rankSep?: number
|
|
277
298
|
nodeSep?: number
|
|
278
299
|
}
|
|
279
|
-
export interface ComputedElementView
|
|
280
|
-
|
|
300
|
+
export interface ComputedElementView<
|
|
301
|
+
ViewIDs extends string = string,
|
|
302
|
+
Tags extends string = string
|
|
303
|
+
> extends Omit<ElementView<ViewIDs, Tags>, 'rules' | 'docUri'>, ViewWithHash, ViewWithNotation {
|
|
304
|
+
readonly extends?: ViewID<ViewIDs>
|
|
281
305
|
readonly autoLayout: ViewAutoLayout
|
|
282
306
|
readonly nodes: ComputedNode[]
|
|
283
307
|
readonly edges: ComputedEdge[]
|
|
284
308
|
rules?: never
|
|
285
309
|
docUri?: never
|
|
286
310
|
}
|
|
287
|
-
export interface ComputedDynamicView
|
|
288
|
-
extends
|
|
289
|
-
|
|
311
|
+
export interface ComputedDynamicView<
|
|
312
|
+
ViewIDs extends string = string,
|
|
313
|
+
Tags extends string = string
|
|
314
|
+
> extends Omit<DynamicView<ViewIDs, Tags>, 'rules' | 'steps' | 'docUri'>, ViewWithHash, ViewWithNotation {
|
|
290
315
|
readonly autoLayout: ViewAutoLayout
|
|
291
316
|
readonly nodes: ComputedNode[]
|
|
292
317
|
readonly edges: ComputedEdge[]
|
|
@@ -298,7 +323,10 @@ export function isComputedDynamicView(view: ComputedView): view is ComputedDynam
|
|
|
298
323
|
return view.__ === 'dynamic'
|
|
299
324
|
}
|
|
300
325
|
|
|
301
|
-
export type ComputedView
|
|
326
|
+
export type ComputedView<
|
|
327
|
+
ViewIDs extends string = string,
|
|
328
|
+
Tags extends string = string
|
|
329
|
+
> = ComputedElementView<ViewIDs, Tags> | ComputedDynamicView<ViewIDs, Tags>
|
|
302
330
|
|
|
303
331
|
export function isComputedElementView(view: ComputedView): view is ComputedElementView {
|
|
304
332
|
return isNullish(view.__) || view.__ === 'element'
|
|
@@ -343,7 +371,10 @@ export interface DiagramEdge extends ComputedEdge {
|
|
|
343
371
|
dotpos?: string
|
|
344
372
|
}
|
|
345
373
|
|
|
346
|
-
export interface DiagramView
|
|
374
|
+
export interface DiagramView<
|
|
375
|
+
ViewIDs extends string = string,
|
|
376
|
+
Tags extends string = string
|
|
377
|
+
> extends Omit<ComputedView<ViewIDs, Tags>, 'nodes' | 'edges' | 'manualLayout'> {
|
|
347
378
|
readonly nodes: DiagramNode[]
|
|
348
379
|
readonly edges: DiagramEdge[]
|
|
349
380
|
readonly bounds: BBox
|
package/src/utils/fqn.ts
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
|
+
import type { LiteralUnion } from 'type-fest'
|
|
1
2
|
import type { Element, Fqn } from '../types'
|
|
2
3
|
import { compareNatural } from './compare-natural'
|
|
3
4
|
import { isString } from './guards'
|
|
4
5
|
|
|
5
6
|
type Predicate<T> = (x: T) => boolean
|
|
6
7
|
|
|
7
|
-
export function nameFromFqn(fqn: Fqn) {
|
|
8
|
+
export function nameFromFqn(fqn: LiteralUnion<Fqn, string>) {
|
|
8
9
|
const lastDot = fqn.lastIndexOf('.')
|
|
9
10
|
if (lastDot > 0) {
|
|
10
11
|
return fqn.slice(lastDot + 1)
|
|
@@ -37,7 +38,7 @@ export function notDescendantOf(ancestors: Element[]): (e: Element) => boolean {
|
|
|
37
38
|
return (e: Element) => !isDescendant(e)
|
|
38
39
|
}
|
|
39
40
|
|
|
40
|
-
export function commonAncestor(first: Fqn
|
|
41
|
+
export function commonAncestor<IDs extends string>(first: Fqn<IDs>, second: Fqn<IDs>) {
|
|
41
42
|
const parentA = parentFqn(first)
|
|
42
43
|
const parentB = parentFqn(second)
|
|
43
44
|
if (parentA === parentB) {
|
|
@@ -49,20 +50,20 @@ export function commonAncestor(first: Fqn, second: Fqn) {
|
|
|
49
50
|
|
|
50
51
|
const a = first.split('.')
|
|
51
52
|
const b = second.split('.')
|
|
52
|
-
let ancestor: Fqn | null = null
|
|
53
|
+
let ancestor: Fqn<IDs> | null = null
|
|
53
54
|
|
|
54
55
|
while (a.length > 1 && b.length > 1 && !!a[0] && a[0] === b[0]) {
|
|
55
|
-
ancestor = (ancestor ? `${ancestor}.${a[0]}` : a[0]) as Fqn
|
|
56
|
+
ancestor = (ancestor ? `${ancestor}.${a[0]}` : a[0]) as Fqn<IDs>
|
|
56
57
|
a.shift()
|
|
57
58
|
b.shift()
|
|
58
59
|
}
|
|
59
60
|
return ancestor
|
|
60
61
|
}
|
|
61
62
|
|
|
62
|
-
export function parentFqn(fqn: Fqn): Fqn | null {
|
|
63
|
+
export function parentFqn<IDs extends string>(fqn: Fqn<IDs>): Fqn<IDs> | null {
|
|
63
64
|
const lastDot = fqn.lastIndexOf('.')
|
|
64
65
|
if (lastDot > 0) {
|
|
65
|
-
return fqn.slice(0, lastDot) as Fqn
|
|
66
|
+
return fqn.slice(0, lastDot) as Fqn<IDs>
|
|
66
67
|
}
|
|
67
68
|
return null
|
|
68
69
|
}
|
|
@@ -76,20 +77,20 @@ export function parentFqnPredicate<T extends { parent: Fqn | null }>(parent: Fqn
|
|
|
76
77
|
* Get all ancestor elements (i.e. parent, parent’s parent, etc.)
|
|
77
78
|
* (from closest to root)
|
|
78
79
|
*/
|
|
79
|
-
export function ancestorsFqn(fqn: Fqn): Fqn[] {
|
|
80
|
-
const path = fqn.split('.')
|
|
80
|
+
export function ancestorsFqn<IDs extends string>(fqn: Fqn<IDs>): Fqn<IDs>[] {
|
|
81
|
+
const path = fqn.split('.') as Fqn<IDs>[]
|
|
81
82
|
path.pop()
|
|
82
83
|
if (path.length === 0) {
|
|
83
84
|
return []
|
|
84
85
|
}
|
|
85
86
|
return path.reduce((acc, part, idx) => {
|
|
86
87
|
if (idx === 0) {
|
|
87
|
-
acc.push(part
|
|
88
|
+
acc.push(part)
|
|
88
89
|
return acc
|
|
89
90
|
}
|
|
90
|
-
acc.unshift(`${acc[0]}.${part}` as Fqn)
|
|
91
|
+
acc.unshift(`${acc[0]}.${part}` as Fqn<IDs>)
|
|
91
92
|
return acc
|
|
92
|
-
}, [] as Fqn[])
|
|
93
|
+
}, [] as Fqn<IDs>[])
|
|
93
94
|
}
|
|
94
95
|
|
|
95
96
|
/**
|