@formicoidea/labre-framework-ddd-context-map 0.31.0 → 0.33.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.
@@ -1,107 +1,23 @@
1
- import { addBubble, addCloud, addLegend, addRelationship, CLOUD, CM_BUBBLE, CM_RELATIONSHIPS, DddMenuBase, } from '@formicoidea/labre-ddd-shared';
2
- import { html, svg } from 'lit';
3
- const bubbleSwatch = svg `<svg viewBox="0 0 24 24" fill="none"><rect x="2" y="7" width="20" height="10" rx="5" fill="#e6f0fa" stroke="#2f6fb0" stroke-width="1.6"/></svg>`;
4
- const cloudSwatch = svg `<svg viewBox="0 0 24 24" fill="none"><path d="M6 17 C3 17 2 14 4.5 12.5 C4 9 8 8 9.5 10 C11 6.5 16 7.5 16 11 C19 10.5 20.5 14 18 16 C18 17 16.5 17 15 17 Z" fill="#f0eef6" stroke="#6d6e71" stroke-width="1.4"/></svg>`;
5
- const legendSwatch = svg `<svg viewBox="0 0 24 24" fill="none"><rect x="3" y="4" width="18" height="16" rx="2" stroke="currentColor" stroke-width="1.6"/><circle cx="7" cy="9" r="1.6" fill="currentColor"/><circle cx="7" cy="14" r="1.6" fill="currentColor"/><path d="M11 9 H18 M11 14 H18" stroke="currentColor" stroke-width="1.4"/></svg>`;
6
- const relationSwatch = (dashed, arrow) => svg `<svg viewBox="0 0 24 24" fill="none"><path d="M3 12 H${arrow ? 17 : 21}" stroke="currentColor" stroke-width="2" stroke-dasharray="${dashed ? '3 3' : '0'}"/>${arrow ? svg `<path d="M15 8 L21 12 L15 16" stroke="currentColor" stroke-width="2" fill="none"/>` : ''}</svg>`;
7
- /** Context Map palette: bounded-context bubble, the cloud, the nine relationship patterns. */
8
- export class EdgelessDddContextMapMenu extends DddMenuBase {
1
+ import { EmptyTool } from '@formicoidea/labre-core/gfx/pointer';
2
+ import { EdgelessCommandMenu } from '@formicoidea/labre-core/widgets/edgeless-toolbar';
3
+ import { css } from 'lit';
4
+ /**
5
+ * Context Map palette, rendered from `contextMapCommands` for the
6
+ * `senior-menu` surface (`docs/adr/0008`). Keeps the DDD palettes' tighter gap
7
+ * it is the widest one, at 13 buttons.
8
+ */
9
+ export class EdgelessDddContextMapMenu extends EdgelessCommandMenu {
9
10
  constructor() {
10
11
  super(...arguments);
11
- this.framework = 'context-map';
12
- }
13
- _createBubble() {
14
- const surface = this.surface;
15
- if (!surface)
16
- return;
17
- const { cx, cy } = this.center;
18
- const id = addBubble(surface, cx, cy, 'Bounded Context');
19
- this.track('FrameworkElementAdded', 'bounded-context');
20
- this.finish(id);
21
- }
22
- _createCloud() {
23
- const surface = this.surface;
24
- if (!surface)
25
- return;
26
- const { cx, cy } = this.center;
27
- const id = addCloud(surface, this.edgeless.std, cx, cy, 'System');
28
- this.track('FrameworkElementAdded', 'cloud');
29
- this.finish(id);
30
- }
31
- _createRelationship(preset) {
32
- const surface = this.surface;
33
- if (!surface)
34
- return;
35
- const { cx, cy } = this.center;
36
- const id = addRelationship(surface, this.edgeless.std, cx, cy, preset);
37
- this.track('FrameworkElementAdded', `relationship:${preset.kind}`);
38
- this.finish(id);
39
- }
40
- _createLegend() {
41
- const surface = this.surface;
42
- if (!surface)
43
- return;
44
- const { cx, cy } = this.center;
45
- const patRows = (kinds) => CM_RELATIONSHIPS.filter(r => kinds.includes(r.kind)).map((r) => ({
46
- swatch: 'line',
47
- color: '#1f2328',
48
- label: `${r.abbrev} — ${r.label}`,
49
- }));
50
- const sections = [
51
- {
52
- title: 'Boundaries',
53
- rows: [
54
- { swatch: 'square', color: CM_BUBBLE.fill, label: 'Bounded Context' },
55
- { swatch: 'square', color: CLOUD.fill, label: 'System / Big Ball of Mud' },
56
- ],
57
- },
58
- { title: 'Mutually dependent', rows: patRows(['partnership', 'sharedKernel']) },
59
- {
60
- title: 'Upstream → Downstream (U/D)',
61
- rows: patRows(['customerSupplier', 'conformist', 'acl', 'ohs', 'publishedLanguage']),
62
- },
63
- { title: 'Separate / no integration', rows: patRows(['separateWays', 'bbom']) },
64
- ];
65
- const id = addLegend(surface, this.edgeless.std, cx - 140, cy - 210, {
66
- title: 'Légende',
67
- sections,
68
- width: 290,
69
- });
70
- this.track('FrameworkElementAdded', 'legend');
71
- this.finish(id);
72
- }
73
- render() {
74
- return html `
75
- <edgeless-slide-menu>
76
- <div class="menu-content">
77
- <div class="button-group-container">
78
- <edgeless-tool-icon-button
79
- .tooltip=${'Bounded Context'}
80
- @click=${() => this._createBubble()}
81
- >
82
- ${bubbleSwatch}
83
- </edgeless-tool-icon-button>
84
- <edgeless-tool-icon-button
85
- .tooltip=${'Cloud / System (Big Ball of Mud)'}
86
- @click=${() => this._createCloud()}
87
- >
88
- ${cloudSwatch}
89
- </edgeless-tool-icon-button>
90
- ${CM_RELATIONSHIPS.map(preset => html `<edgeless-tool-icon-button
91
- .tooltip=${preset.label}
92
- @click=${() => this._createRelationship(preset)}
93
- >
94
- ${relationSwatch(preset.dashed, preset.upDown)}
95
- </edgeless-tool-icon-button>`)}
96
- <edgeless-tool-icon-button
97
- .tooltip=${'Legend'}
98
- @click=${() => this._createLegend()}
99
- >
100
- ${legendSwatch}
101
- </edgeless-tool-icon-button>
102
- </div>
103
- </div>
104
- </edgeless-slide-menu>
105
- `;
12
+ this.owner = 'ddd-context-map';
13
+ this.type = EmptyTool;
106
14
  }
15
+ static { this.styles = [
16
+ EdgelessCommandMenu.styles,
17
+ css `
18
+ :host {
19
+ --labre-command-menu-gap: 10px;
20
+ }
21
+ `,
22
+ ]; }
107
23
  }
@@ -2,5 +2,6 @@ import { DddSeniorButtonBase } from '@formicoidea/labre-ddd-shared';
2
2
  export declare class EdgelessDddContextMapSeniorButton extends DddSeniorButtonBase {
3
3
  protected menuTag: "edgeless-ddd-context-map-menu";
4
4
  protected label: string;
5
+ protected labelKey: string;
5
6
  protected icon: import("lit-html").TemplateResult<2>;
6
7
  }
@@ -4,6 +4,7 @@ export class EdgelessDddContextMapSeniorButton extends DddSeniorButtonBase {
4
4
  super(...arguments);
5
5
  this.menuTag = 'edgeless-ddd-context-map-menu';
6
6
  this.label = 'Context Map';
7
+ this.labelKey = 'com.labre.framework.ddd-context-map';
7
8
  this.icon = contextMapToolbarIcon;
8
9
  }
9
10
  }
@@ -3,6 +3,7 @@ import { html } from 'lit';
3
3
  /** Independent senior tool — Context Map. */
4
4
  export const contextMapSeniorTool = SeniorToolExtension('ddd-context-map', ({ block }) => ({
5
5
  name: 'Context Map',
6
+ labelKey: 'com.labre.framework.ddd-context-map',
6
7
  content: html `<edgeless-ddd-context-map-senior-button
7
8
  .edgeless=${block}
8
9
  ></edgeless-ddd-context-map-senior-button>`,
@@ -0,0 +1,14 @@
1
+ import { type TranslationKeyManifestEntry } from '@formicoidea/labre-core/std';
2
+ /**
3
+ * THIS framework's contribution to the translation-key manifest — every
4
+ * `com.labre.*` key Context Mapping can hand to `TranslationProvider.t`,
5
+ * derived from the very declarations the editor registers (never restated).
6
+ *
7
+ * It lives HERE, not in `@labre/affine/translations`, because the bundled
8
+ * distribution splits the library along exactly this line:
9
+ * `@formicoidea/labre-core` is the editor MINUS the frameworks, and a host that
10
+ * installs `@formicoidea/labre-framework-ddd-context-map` composes this export
11
+ * into the catalogue it builds — the same sentence that already holds for
12
+ * `contextMapCommands`. See `packages/affine/all/src/translations.ts`.
13
+ */
14
+ export declare const contextMapTranslationEntries: TranslationKeyManifestEntry[];
@@ -0,0 +1,20 @@
1
+ import { collectTranslationKeys, commandTranslationEntries, mergeTranslationEntries, } from '@formicoidea/labre-core/std';
2
+ import { CONTEXT_MAP_BACKGROUND } from './background.js';
3
+ import { contextMapCommands } from './commands.js';
4
+ import { CONTEXT_MAP_NUDGES } from './nudges.js';
5
+ import { CONTEXT_MAP_PROFILES } from './profiles.js';
6
+ import { CONTEXT_MAP_ROLES } from './roles.js';
7
+ import { CONTEXT_MAP_RULES } from './rules.js';
8
+ /**
9
+ * THIS framework's contribution to the translation-key manifest — every
10
+ * `com.labre.*` key Context Mapping can hand to `TranslationProvider.t`,
11
+ * derived from the very declarations the editor registers (never restated).
12
+ *
13
+ * It lives HERE, not in `@labre/affine/translations`, because the bundled
14
+ * distribution splits the library along exactly this line:
15
+ * `@formicoidea/labre-core` is the editor MINUS the frameworks, and a host that
16
+ * installs `@formicoidea/labre-framework-ddd-context-map` composes this export
17
+ * into the catalogue it builds — the same sentence that already holds for
18
+ * `contextMapCommands`. See `packages/affine/all/src/translations.ts`.
19
+ */
20
+ export const contextMapTranslationEntries = mergeTranslationEntries(commandTranslationEntries(contextMapCommands), collectTranslationKeys('role', CONTEXT_MAP_ROLES), collectTranslationKeys('background', CONTEXT_MAP_BACKGROUND), collectTranslationKeys('rule', CONTEXT_MAP_RULES), collectTranslationKeys('nudge', CONTEXT_MAP_NUDGES), collectTranslationKeys('profile', CONTEXT_MAP_PROFILES));
package/dist/view.d.ts CHANGED
@@ -1,6 +1,22 @@
1
1
  import { type ViewExtensionContext, ViewExtensionProvider } from '@formicoidea/labre-core/ext-loader';
2
2
  /**
3
- * Context Map — independently flag-gated (`ddd-context-map`).
3
+ * Context Map rendering ALWAYS registered, independent of any flag.
4
+ * Disabling `ddd-context-map` hides only the creation tooling (see
5
+ * {@link DddContextMapViewExtension}); boards already drawn must still paint,
6
+ * stay selectable, stay movable and keep their contextual toolbar. See
7
+ * `docs/adr/0009`.
8
+ */
9
+ export declare class DddContextMapRenderViewExtension extends ViewExtensionProvider {
10
+ name: string;
11
+ setup(context: ViewExtensionContext): void;
12
+ }
13
+ /**
14
+ * Context Map creation tooling — independently flag-gated
15
+ * (`ddd-context-map`): the senior toolbar button, its palette and the
16
+ * validation rules, profiles and quality nudges. Both halves are tooling: a map
17
+ * drawn while the flag was on keeps rendering when it goes off, it just stops
18
+ * being checked — and the profile it was put on stays written, unread, until the
19
+ * flag comes back.
4
20
  *
5
21
  * Note: its Templates-panel category is registered by the aggregate package's
6
22
  * {@link DddTemplatesViewExtension} (gated by `ddd-templates`), so templates
package/dist/view.js CHANGED
@@ -1,8 +1,54 @@
1
+ import { QualityNudgeExtension, validationToolbarConfig, ValidationProfileExtension, ValidationRuleExtension, } from '@formicoidea/labre-core/blocks/surface';
1
2
  import { ViewExtensionProvider, } from '@formicoidea/labre-core/ext-loader';
3
+ import { ToolbarModuleExtension } from '@formicoidea/labre-core/shared/services';
4
+ import { BlockFlavourIdentifier, CommandExtension } from '@formicoidea/labre-core/std';
5
+ import { RoleVocabularyExtension } from '@formicoidea/labre-core/std/gfx';
6
+ import { contextMapCommandIcons, contextMapCommands } from './commands.js';
2
7
  import { contextMapEffects } from './effects.js';
8
+ import { ContextMapRendererExtension } from './element-renderer.js';
9
+ import { ContextMapInteraction, ContextMapView } from './element-view.js';
10
+ import { CONTEXT_MAP_NUDGES } from './nudges.js';
11
+ import { CONTEXT_MAP_PROFILES } from './profiles.js';
12
+ import { CONTEXT_MAP_ROLES } from './roles.js';
13
+ import { CONTEXT_MAP_RULES } from './rules.js';
14
+ import { contextMapBoardToolbarExtension } from './toolbar/board-config.js';
3
15
  import { contextMapSeniorTool } from './toolbar/senior-tool.js';
4
16
  /**
5
- * Context Map — independently flag-gated (`ddd-context-map`).
17
+ * Context Map rendering ALWAYS registered, independent of any flag.
18
+ * Disabling `ddd-context-map` hides only the creation tooling (see
19
+ * {@link DddContextMapViewExtension}); boards already drawn must still paint,
20
+ * stay selectable, stay movable and keep their contextual toolbar. See
21
+ * `docs/adr/0009`.
22
+ */
23
+ export class DddContextMapRenderViewExtension extends ViewExtensionProvider {
24
+ constructor() {
25
+ super(...arguments);
26
+ this.name = 'affine-ddd-context-map-render-gfx';
27
+ }
28
+ setup(context) {
29
+ super.setup(context);
30
+ context.register(ContextMapView);
31
+ context.register(ContextMapRendererExtension);
32
+ // The role VOCABULARY, always on. A role is written in the DOCUMENT, not in
33
+ // the tooling: the direction reveal of a typed relationship, the inversion
34
+ // command and the toolbar entry that must not lie about one all read this,
35
+ // and they have to keep working on a map drawn while the flag was on and
36
+ // opened while it is off (`docs/adr/0009`, `docs/adr/0010`). The rules that
37
+ // JUDGE those roles stay in the flag-gated extension below.
38
+ context.register(RoleVocabularyExtension(CONTEXT_MAP_ROLES));
39
+ if (this.isEdgeless(context.scope)) {
40
+ context.register(ContextMapInteraction);
41
+ context.register(contextMapBoardToolbarExtension);
42
+ }
43
+ }
44
+ }
45
+ /**
46
+ * Context Map creation tooling — independently flag-gated
47
+ * (`ddd-context-map`): the senior toolbar button, its palette and the
48
+ * validation rules, profiles and quality nudges. Both halves are tooling: a map
49
+ * drawn while the flag was on keeps rendering when it goes off, it just stops
50
+ * being checked — and the profile it was put on stays written, unread, until the
51
+ * flag comes back.
6
52
  *
7
53
  * Note: its Templates-panel category is registered by the aggregate package's
8
54
  * {@link DddTemplatesViewExtension} (gated by `ddd-templates`), so templates
@@ -20,7 +66,22 @@ export class DddContextMapViewExtension extends ViewExtensionProvider {
20
66
  setup(context) {
21
67
  super.setup(context);
22
68
  if (this.isEdgeless(context.scope)) {
69
+ context.register(ValidationRuleExtension(CONTEXT_MAP_RULES));
70
+ context.register(ValidationProfileExtension(CONTEXT_MAP_PROFILES));
71
+ context.register(QualityNudgeExtension(CONTEXT_MAP_NUDGES));
72
+ // The Validation dropdown on a selected board's contextual toolbar. A
73
+ // SECOND module on the same element, through the `custom:` flavour slot:
74
+ // `contextMapBoardToolbarExtension` is registered always-on because a
75
+ // stored board must keep its resize toggle, while choosing how hard to
76
+ // check it is tooling and belongs here. The config names no framework —
77
+ // it reads roles and profiles — so it is the very same object Wardley
78
+ // registers on its own flavour.
79
+ context.register(ToolbarModuleExtension({
80
+ id: BlockFlavourIdentifier('custom:affine:surface:contextMap'),
81
+ config: validationToolbarConfig,
82
+ }));
23
83
  context.register(contextMapSeniorTool);
84
+ context.register(CommandExtension(contextMapCommands, contextMapCommandIcons));
24
85
  }
25
86
  }
26
87
  }
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@formicoidea/labre-framework-ddd-context-map",
3
3
  "description": "Labre ddd-context-map framework for @formicoidea/labre-core.",
4
- "version": "0.31.0",
4
+ "version": "0.33.0",
5
5
  "type": "module",
6
6
  "sideEffects": false,
7
7
  "author": "lajola",
@@ -27,8 +27,8 @@
27
27
  "dist"
28
28
  ],
29
29
  "dependencies": {
30
- "@formicoidea/labre-core": "0.31.0",
31
- "@formicoidea/labre-ddd-shared": "0.31.0",
30
+ "@formicoidea/labre-core": "0.33.0",
31
+ "@formicoidea/labre-ddd-shared": "0.33.0",
32
32
  "lit": "^3.2.0"
33
33
  }
34
34
  }