@things-factory/integration-ui 7.0.31 → 7.0.35

Sign up to get free protection for your applications and to get access to all the features.
Files changed (34) hide show
  1. package/client/analysis/graph-data.ts +34 -0
  2. package/client/analysis/graph-viewer-old.ts +1097 -0
  3. package/client/analysis/graph-viewer-style.ts +5 -1
  4. package/client/analysis/graph-viewer.ts +245 -942
  5. package/client/analysis/node.ts +73 -0
  6. package/client/analysis/relationship.ts +19 -0
  7. package/client/analysis/utils.ts +41 -0
  8. package/client/pages/integration-analysis.ts +160 -71
  9. package/dist-client/analysis/graph-data.d.ts +36 -0
  10. package/dist-client/analysis/graph-data.js +2 -0
  11. package/dist-client/analysis/graph-data.js.map +1 -0
  12. package/dist-client/analysis/graph-viewer-old.d.ts +110 -0
  13. package/dist-client/analysis/graph-viewer-old.js +808 -0
  14. package/dist-client/analysis/graph-viewer-old.js.map +1 -0
  15. package/dist-client/analysis/graph-viewer-style.js +5 -1
  16. package/dist-client/analysis/graph-viewer-style.js.map +1 -1
  17. package/dist-client/analysis/graph-viewer.d.ts +25 -99
  18. package/dist-client/analysis/graph-viewer.js +189 -703
  19. package/dist-client/analysis/graph-viewer.js.map +1 -1
  20. package/dist-client/analysis/node.d.ts +4 -0
  21. package/dist-client/analysis/node.js +59 -0
  22. package/dist-client/analysis/node.js.map +1 -0
  23. package/dist-client/analysis/relationship.d.ts +4 -0
  24. package/dist-client/analysis/relationship.js +13 -0
  25. package/dist-client/analysis/relationship.js.map +1 -0
  26. package/dist-client/analysis/utils.d.ts +20 -0
  27. package/dist-client/analysis/utils.js +31 -0
  28. package/dist-client/analysis/utils.js.map +1 -0
  29. package/dist-client/pages/integration-analysis.d.ts +8 -3
  30. package/dist-client/pages/integration-analysis.js +153 -70
  31. package/dist-client/pages/integration-analysis.js.map +1 -1
  32. package/dist-client/tsconfig.tsbuildinfo +1 -1
  33. package/dist-server/tsconfig.tsbuildinfo +1 -1
  34. package/package.json +6 -6
@@ -1,7 +1,7 @@
1
1
  import { __decorate, __metadata } from "tslib";
2
2
  import '../analysis/graph-viewer';
3
3
  import gql from 'graphql-tag';
4
- import { css, html } from 'lit';
4
+ import { css, html, nothing } from 'lit';
5
5
  import { customElement, query, state } from 'lit/decorators.js';
6
6
  import { client } from '@operato/graphql';
7
7
  import { i18next, localize } from '@operato/i18n';
@@ -13,84 +13,84 @@ let IntegrationAnalysis = class IntegrationAnalysis extends localize(i18next)(Pa
13
13
  get context() {
14
14
  return {
15
15
  title: i18next.t('text.integration analysis'),
16
+ search: {
17
+ handler: search => this.onSearch(search)
18
+ },
16
19
  help: 'integration/ui/integration-analysis'
17
20
  };
18
21
  }
19
22
  render() {
20
- return html `<div graph-container></div>`;
23
+ const info = this.info;
24
+ return html `
25
+ <div
26
+ graph-container
27
+ @node-mouseenter=${(e) => console.log(e.detail)}
28
+ @node-mouseleave=${(e) => console.log(e.detail)}
29
+ ></div>
30
+ <div class="graph-info">
31
+ ${info
32
+ ? html `<a href="#" class="${info.cls}" node-info><strong>${info.property}</strong>${info.value}</a>`
33
+ : nothing}
34
+ </div>
35
+ `;
21
36
  }
22
37
  updated(changes) {
23
38
  if (changes.has('analysis')) {
24
- this.graphViewer = new GraphViewer(this.container, {
25
- highlight: [
26
- {
27
- class: 'Connection',
28
- property: 'missing',
29
- value: true
30
- },
31
- {
32
- class: 'Scenario',
33
- property: 'missing',
34
- value: true
35
- },
36
- {
37
- class: 'Tag',
38
- property: 'missing',
39
- value: true
40
- }
41
- ],
42
- icons: {
43
- Connection: 'gear',
44
- Scenario: 'birthday-cake',
45
- Tag: 'paw'
46
- },
47
- // images: {
48
- // Address: 'img/twemoji/1f3e0.svg',
49
- // BirthDate: 'img/twemoji/1f5d3.svg',
50
- // Cookie: 'img/twemoji/1f36a.svg',
51
- // CreditCard: 'img/twemoji/1f4b3.svg',
52
- // Device: 'img/twemoji/1f4bb.svg',
53
- // Email: 'img/twemoji/2709.svg',
54
- // Git: 'img/twemoji/1f5c3.svg',
55
- // Github: 'img/twemoji/1f5c4.svg',
56
- // icons: 'img/twemoji/1f38f.svg',
57
- // Ip: 'img/twemoji/1f4cd.svg',
58
- // Issues: 'img/twemoji/1f4a9.svg',
59
- // Language: 'img/twemoji/1f1f1-1f1f7.svg',
60
- // Options: 'img/twemoji/2699.svg',
61
- // Password: 'img/twemoji/1f511.svg',
62
- // 'Project|name|d3': 'img/twemoji/32-20e3.svg',
63
- // User: 'img/twemoji/1f600.svg'
64
- // },
65
- minCollision: 60,
66
- graphData: {
67
- results: [
39
+ if (!this.graphViewer) {
40
+ this.graphViewer = new GraphViewer(this.container, {
41
+ highlight: [
42
+ {
43
+ class: 'Connection',
44
+ property: 'missing',
45
+ value: true
46
+ },
68
47
  {
69
- columns: ['Connection', 'Scenario', 'Tag'],
70
- data: [
71
- {
72
- graph: this.analysis
73
- }
74
- ]
48
+ class: 'Scenario',
49
+ property: 'missing',
50
+ value: true
51
+ },
52
+ {
53
+ class: 'Tag',
54
+ property: 'missing',
55
+ value: true
75
56
  }
76
57
  ],
58
+ minCollision: 60,
59
+ graphData: {
60
+ results: [
61
+ {
62
+ columns: [],
63
+ data: [
64
+ {
65
+ graph: this.analysis
66
+ }
67
+ ]
68
+ }
69
+ ],
70
+ errors: []
71
+ },
72
+ nodeRadius: 25,
73
+ onNodeDoubleClick: node => {
74
+ switch (node.id) {
75
+ case '25':
76
+ // Google
77
+ window.open(node.properties.url, '_blank');
78
+ break;
79
+ default:
80
+ break;
81
+ }
82
+ },
83
+ zoomFit: true
84
+ });
85
+ }
86
+ else {
87
+ this.graphViewer.updateWithGraphData({
88
+ results: [{ columns: [], data: [{ graph: this.analysis }] }],
77
89
  errors: []
78
- },
79
- nodeRadius: 25,
80
- onNodeDoubleClick: node => {
81
- switch (node.id) {
82
- case '25':
83
- // Google
84
- window.open(node.properties.url, '_blank');
85
- break;
86
- default:
87
- var maxNodes = 5, data = this.graphViewer.randomD3Data(node, maxNodes);
88
- this.graphViewer.updateWithD3Data(data);
89
- break;
90
- }
91
- },
92
- zoomFit: true
93
- });
90
+ });
91
+ }
92
+ }
93
+ if (changes.has('info') && this.info) {
94
94
  }
95
95
  }
96
96
  async pageUpdated(changes) {
@@ -115,12 +115,80 @@ let IntegrationAnalysis = class IntegrationAnalysis extends localize(i18next)(Pa
115
115
  });
116
116
  this.analysis = response.data.integrationAnalysis;
117
117
  }
118
+ async onSearch(search) {
119
+ if (!this.graphViewer) {
120
+ return;
121
+ }
122
+ if (!search) {
123
+ this.graphViewer.updateWithGraphData({
124
+ results: [{ columns: [], data: [{ graph: this.analysis }] }],
125
+ errors: []
126
+ });
127
+ return;
128
+ }
129
+ const { nodes = [], relationships = [] } = this.analysis || {};
130
+ // 검색어와 일치하는 노드를 필터링
131
+ const matchingNodes = nodes.filter(node => {
132
+ return node.properties.name && node.properties.name.toLowerCase().includes(search.toLowerCase());
133
+ });
134
+ if (matchingNodes.length === 0) {
135
+ this.graphViewer.updateWithGraphData({
136
+ results: [{ columns: [], data: [{ graph: { nodes: [], relationships: [] } }] }],
137
+ errors: []
138
+ });
139
+ return;
140
+ }
141
+ // 1차로 연결된 노드와 관계를 찾기 위해 관련된 노드 ID를 추적
142
+ const relatedNodeIds = new Set();
143
+ const filteredNodes = [];
144
+ const filteredRelationships = [];
145
+ matchingNodes.forEach(node => {
146
+ relatedNodeIds.add(node.id);
147
+ filteredNodes.push(node);
148
+ relationships.forEach(relationship => {
149
+ const { source, target } = relationship || {};
150
+ if (source.id === node.id || target.id === node.id) {
151
+ relatedNodeIds.add(source.id);
152
+ relatedNodeIds.add(target.id);
153
+ filteredRelationships.push(relationship);
154
+ }
155
+ });
156
+ });
157
+ // 관련된 노드 추가
158
+ relatedNodeIds.forEach(nodeId => {
159
+ const node = nodes.find(n => n.id === nodeId);
160
+ if (node) {
161
+ filteredNodes.push(node);
162
+ }
163
+ });
164
+ // 새로운 GraphData 구성
165
+ const filteredGraphData = {
166
+ results: [
167
+ {
168
+ columns: [],
169
+ data: [
170
+ {
171
+ graph: {
172
+ nodes: filteredNodes,
173
+ relationships: filteredRelationships
174
+ }
175
+ }
176
+ ]
177
+ }
178
+ ],
179
+ errors: []
180
+ };
181
+ // GraphViewer 업데이트
182
+ this.graphViewer.updateWithGraphData(filteredGraphData);
183
+ }
118
184
  };
119
185
  IntegrationAnalysis.styles = [
120
186
  GraphViewerStyles,
121
187
  ScrollbarStyles,
122
188
  css `
123
189
  :host {
190
+ position: relative;
191
+
124
192
  display: flex;
125
193
  flex-direction: column;
126
194
 
@@ -134,20 +202,35 @@ IntegrationAnalysis.styles = [
134
202
  margin: 0;
135
203
  padding: 0;
136
204
  }
205
+
206
+ .graph-info {
207
+ position: absolute;
208
+ top: 10px;
209
+ left: 10px;
210
+ opacity: 0.8;
211
+ }
137
212
  `
138
213
  ];
214
+ __decorate([
215
+ state(),
216
+ __metadata("design:type", GraphViewer)
217
+ ], IntegrationAnalysis.prototype, "graphViewer", void 0);
139
218
  __decorate([
140
219
  state(),
141
220
  __metadata("design:type", Object)
142
221
  ], IntegrationAnalysis.prototype, "analysis", void 0);
143
222
  __decorate([
144
223
  state(),
145
- __metadata("design:type", GraphViewer)
146
- ], IntegrationAnalysis.prototype, "graphViewer", void 0);
224
+ __metadata("design:type", Object)
225
+ ], IntegrationAnalysis.prototype, "info", void 0);
147
226
  __decorate([
148
227
  query('[graph-container]'),
149
228
  __metadata("design:type", HTMLDivElement)
150
229
  ], IntegrationAnalysis.prototype, "container", void 0);
230
+ __decorate([
231
+ query('[node-info]'),
232
+ __metadata("design:type", HTMLAnchorElement)
233
+ ], IntegrationAnalysis.prototype, "nodeInfo", void 0);
151
234
  IntegrationAnalysis = __decorate([
152
235
  customElement('integration-analysis')
153
236
  ], IntegrationAnalysis);
@@ -1 +1 @@
1
- {"version":3,"file":"integration-analysis.js","sourceRoot":"","sources":["../../client/pages/integration-analysis.ts"],"names":[],"mappings":"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","sourcesContent":["import '../analysis/graph-viewer'\n\nimport gql from 'graphql-tag'\nimport { css, html } from 'lit'\nimport { customElement, query, state } from 'lit/decorators.js'\n\nimport { client } from '@operato/graphql'\nimport { i18next, localize } from '@operato/i18n'\nimport { PageView } from '@operato/shell'\nimport { ScrollbarStyles } from '@operato/styles'\nimport { GraphViewer } from '../analysis/graph-viewer'\nimport { GraphViewerStyles } from '../analysis/graph-viewer-style'\n\n@customElement('integration-analysis')\nexport class IntegrationAnalysis extends localize(i18next)(PageView) {\n static styles = [\n GraphViewerStyles,\n ScrollbarStyles,\n css`\n :host {\n display: flex;\n flex-direction: column;\n\n overflow: hidden;\n background-color: var(--md-sys-color-background);\n padding: 0;\n }\n\n [graph-container] {\n flex: 1;\n margin: 0;\n padding: 0;\n }\n `\n ]\n\n @state() analysis: any\n @state() graphViewer?: GraphViewer\n\n @query('[graph-container]') container!: HTMLDivElement\n\n get context() {\n return {\n title: i18next.t('text.integration analysis'),\n help: 'integration/ui/integration-analysis'\n }\n }\n\n render() {\n return html`<div graph-container></div>`\n }\n\n updated(changes) {\n if (changes.has('analysis')) {\n this.graphViewer = new GraphViewer(this.container, {\n highlight: [\n {\n class: 'Connection',\n property: 'missing',\n value: true\n },\n {\n class: 'Scenario',\n property: 'missing',\n value: true\n },\n {\n class: 'Tag',\n property: 'missing',\n value: true\n }\n ],\n icons: {\n Connection: 'gear',\n Scenario: 'birthday-cake',\n Tag: 'paw'\n },\n // images: {\n // Address: 'img/twemoji/1f3e0.svg',\n // BirthDate: 'img/twemoji/1f5d3.svg',\n // Cookie: 'img/twemoji/1f36a.svg',\n // CreditCard: 'img/twemoji/1f4b3.svg',\n // Device: 'img/twemoji/1f4bb.svg',\n // Email: 'img/twemoji/2709.svg',\n // Git: 'img/twemoji/1f5c3.svg',\n // Github: 'img/twemoji/1f5c4.svg',\n // icons: 'img/twemoji/1f38f.svg',\n // Ip: 'img/twemoji/1f4cd.svg',\n // Issues: 'img/twemoji/1f4a9.svg',\n // Language: 'img/twemoji/1f1f1-1f1f7.svg',\n // Options: 'img/twemoji/2699.svg',\n // Password: 'img/twemoji/1f511.svg',\n // 'Project|name|d3': 'img/twemoji/32-20e3.svg',\n // User: 'img/twemoji/1f600.svg'\n // },\n minCollision: 60,\n graphData: {\n results: [\n {\n columns: ['Connection', 'Scenario', 'Tag'],\n data: [\n {\n graph: this.analysis\n }\n ]\n }\n ],\n errors: []\n },\n nodeRadius: 25,\n onNodeDoubleClick: node => {\n switch (node.id) {\n case '25':\n // Google\n window.open(node.properties.url, '_blank')\n break\n default:\n var maxNodes = 5,\n data = this.graphViewer!.randomD3Data(node, maxNodes)\n this.graphViewer!.updateWithD3Data(data)\n break\n }\n },\n zoomFit: true\n })\n }\n }\n\n async pageUpdated(changes) {\n if ('active' in changes) {\n if (this.active) {\n await this.fetchIntegrationAnalysis()\n this.graphViewer?.simulation.restart()\n } else {\n this.graphViewer?.simulation.stop()\n }\n }\n }\n\n async fetchIntegrationAnalysis() {\n const response = await client.query({\n query: gql`\n query {\n integrationAnalysis\n }\n `\n })\n\n this.analysis = response.data.integrationAnalysis\n }\n}\n"]}
1
+ {"version":3,"file":"integration-analysis.js","sourceRoot":"","sources":["../../client/pages/integration-analysis.ts"],"names":[],"mappings":"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","sourcesContent":["import '../analysis/graph-viewer'\n\nimport gql from 'graphql-tag'\nimport { css, html, nothing } from 'lit'\nimport { customElement, query, state } from 'lit/decorators.js'\n\nimport { client } from '@operato/graphql'\nimport { i18next, localize } from '@operato/i18n'\nimport { PageView } from '@operato/shell'\nimport { ScrollbarStyles } from '@operato/styles'\nimport { GraphData, Node, Relationship } from 'analysis/graph-data'\nimport { GraphViewer } from '../analysis/graph-viewer'\nimport { GraphViewerStyles } from '../analysis/graph-viewer-style'\n\n@customElement('integration-analysis')\nexport class IntegrationAnalysis extends localize(i18next)(PageView) {\n static styles = [\n GraphViewerStyles,\n ScrollbarStyles,\n css`\n :host {\n position: relative;\n\n display: flex;\n flex-direction: column;\n\n overflow: hidden;\n background-color: var(--md-sys-color-background);\n padding: 0;\n }\n\n [graph-container] {\n flex: 1;\n margin: 0;\n padding: 0;\n }\n\n .graph-info {\n position: absolute;\n top: 10px;\n left: 10px;\n opacity: 0.8;\n }\n `\n ]\n\n @state() private graphViewer?: GraphViewer\n @state() private analysis?: { nodes: Node[]; relationships: Relationship[] }\n @state() private info?: { cls: string; property: string; value: string } | null\n\n @query('[graph-container]') container!: HTMLDivElement\n @query('[node-info]') nodeInfo!: HTMLAnchorElement\n\n get context() {\n return {\n title: i18next.t('text.integration analysis'),\n search: {\n handler: search => this.onSearch(search)\n },\n help: 'integration/ui/integration-analysis'\n }\n }\n\n render() {\n const info = this.info\n\n return html`\n <div\n graph-container\n @node-mouseenter=${(e: CustomEvent) => console.log(e.detail)}\n @node-mouseleave=${(e: CustomEvent) => console.log(e.detail)}\n ></div>\n <div class=\"graph-info\">\n ${info\n ? html`<a href=\"#\" class=\"${info.cls}\" node-info><strong>${info.property}</strong>${info.value}</a>`\n : nothing}\n </div>\n `\n }\n\n updated(changes) {\n if (changes.has('analysis')) {\n if (!this.graphViewer) {\n this.graphViewer = new GraphViewer(this.container, {\n highlight: [\n {\n class: 'Connection',\n property: 'missing',\n value: true\n },\n {\n class: 'Scenario',\n property: 'missing',\n value: true\n },\n {\n class: 'Tag',\n property: 'missing',\n value: true\n }\n ],\n minCollision: 60,\n graphData: {\n results: [\n {\n columns: [],\n data: [\n {\n graph: this.analysis\n }\n ]\n }\n ],\n errors: []\n },\n nodeRadius: 25,\n onNodeDoubleClick: node => {\n switch (node.id) {\n case '25':\n // Google\n window.open(node.properties.url, '_blank')\n break\n default:\n break\n }\n },\n zoomFit: true\n })\n } else {\n this.graphViewer.updateWithGraphData({\n results: [{ columns: [], data: [{ graph: this.analysis! }] }],\n errors: []\n })\n }\n }\n\n if (changes.has('info') && this.info) {\n }\n }\n\n async pageUpdated(changes) {\n if ('active' in changes) {\n if (this.active) {\n await this.fetchIntegrationAnalysis()\n this.graphViewer?.simulation.restart()\n } else {\n this.graphViewer?.simulation.stop()\n }\n }\n }\n\n async fetchIntegrationAnalysis() {\n const response = await client.query({\n query: gql`\n query {\n integrationAnalysis\n }\n `\n })\n\n this.analysis = response.data.integrationAnalysis\n }\n\n async onSearch(search: string) {\n if (!this.graphViewer) {\n return\n }\n\n if (!search) {\n this.graphViewer.updateWithGraphData({\n results: [{ columns: [], data: [{ graph: this.analysis! }] }],\n errors: []\n })\n return\n }\n\n const { nodes = [], relationships = [] } = this.analysis || {}\n\n // 검색어와 일치하는 노드를 필터링\n const matchingNodes = nodes.filter(node => {\n return node.properties.name && node.properties.name.toLowerCase().includes(search.toLowerCase())\n })\n\n if (matchingNodes.length === 0) {\n this.graphViewer.updateWithGraphData({\n results: [{ columns: [], data: [{ graph: { nodes: [], relationships: [] } }] }],\n errors: []\n })\n return\n }\n\n // 1차로 연결된 노드와 관계를 찾기 위해 관련된 노드 ID를 추적\n const relatedNodeIds = new Set<string>()\n const filteredNodes = [] as Node[]\n const filteredRelationships = [] as Relationship[]\n\n matchingNodes.forEach(node => {\n relatedNodeIds.add(node.id)\n filteredNodes.push(node)\n\n relationships.forEach(relationship => {\n const { source, target } = relationship || {}\n if (source!.id === node.id || target!.id === node.id) {\n relatedNodeIds.add(source!.id)\n relatedNodeIds.add(target!.id)\n filteredRelationships.push(relationship!)\n }\n })\n })\n\n // 관련된 노드 추가\n relatedNodeIds.forEach(nodeId => {\n const node = nodes.find(n => n.id === nodeId)\n if (node) {\n filteredNodes.push(node)\n }\n })\n\n // 새로운 GraphData 구성\n const filteredGraphData: GraphData = {\n results: [\n {\n columns: [],\n data: [\n {\n graph: {\n nodes: filteredNodes,\n relationships: filteredRelationships\n }\n }\n ]\n }\n ],\n errors: []\n }\n\n // GraphViewer 업데이트\n this.graphViewer.updateWithGraphData(filteredGraphData)\n }\n}\n"]}