node-opcua-address-space 2.164.2 → 2.165.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/source/loader/load_nodeset2.d.ts +6 -4
- package/dist/source/loader/load_nodeset2.js +100 -59
- package/dist/source/loader/load_nodeset2.js.map +1 -1
- package/dist/source/session_context.d.ts +24 -0
- package/dist/source/session_context.js +34 -0
- package/dist/source/session_context.js.map +1 -1
- package/dist/src/address_space.d.ts +13 -1
- package/dist/src/address_space.js +20 -0
- package/dist/src/address_space.js.map +1 -1
- package/dist/src/address_space_private.d.ts +2 -1
- package/dist/src/base_node_impl.d.ts +17 -17
- package/dist/src/base_node_impl.js +78 -58
- package/dist/src/base_node_impl.js.map +1 -1
- package/dist/src/ua_data_type_impl.d.ts +7 -11
- package/dist/src/ua_data_type_impl.js +30 -26
- package/dist/src/ua_data_type_impl.js.map +1 -1
- package/dist/src/ua_method_impl.js +71 -28
- package/dist/src/ua_method_impl.js.map +1 -1
- package/dist/src/ua_variable_impl_ext_obj.js +54 -2
- package/dist/src/ua_variable_impl_ext_obj.js.map +1 -1
- package/dist/tsconfig_base.tsbuildinfo +1 -1
- package/package.json +34 -34
- package/source/loader/load_nodeset2.ts +118 -95
- package/source/session_context.ts +52 -2
- package/src/address_space.ts +24 -1
- package/src/address_space_private.ts +4 -1
- package/src/base_node_impl.ts +142 -135
- package/src/ua_data_type_impl.ts +52 -81
- package/src/ua_method_impl.ts +82 -39
- package/src/ua_variable_impl_ext_obj.ts +46 -2
package/src/base_node_impl.ts
CHANGED
|
@@ -1,89 +1,88 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* @module node-opcua-address-space
|
|
3
3
|
*/
|
|
4
|
-
|
|
4
|
+
|
|
5
|
+
import { EventEmitter } from "node:events";
|
|
5
6
|
import chalk from "chalk";
|
|
6
7
|
import { isEqual } from "lodash";
|
|
7
8
|
|
|
8
|
-
import {
|
|
9
|
+
import type {
|
|
9
10
|
AddReferenceOpts,
|
|
10
|
-
|
|
11
|
+
BaseNode,
|
|
12
|
+
BrowseDescriptionOptions2,
|
|
13
|
+
IAddressSpace,
|
|
14
|
+
INamespace,
|
|
11
15
|
ISessionContext,
|
|
16
|
+
ModellingRuleType,
|
|
12
17
|
UAMethod,
|
|
13
18
|
UAObject,
|
|
14
19
|
UAObjectType,
|
|
20
|
+
UAProperty,
|
|
15
21
|
UAReference,
|
|
16
|
-
UAVariable,
|
|
17
|
-
UAVariableType,
|
|
18
|
-
BaseNode,
|
|
19
22
|
UAReferenceType,
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
BrowseDescriptionOptions2,
|
|
23
|
-
UAVariableT,
|
|
24
|
-
UAProperty
|
|
23
|
+
UAVariable,
|
|
24
|
+
UAVariableType
|
|
25
25
|
} from "node-opcua-address-space-base";
|
|
26
26
|
import { assert } from "node-opcua-assert";
|
|
27
|
+
import type { UAString } from "node-opcua-basic-types";
|
|
28
|
+
import { ObjectTypeIds, ReferenceTypeIds, VariableTypeIds } from "node-opcua-constants";
|
|
27
29
|
import {
|
|
30
|
+
AccessRestrictionsFlag,
|
|
28
31
|
AttributeIds,
|
|
29
32
|
attributeNameById,
|
|
30
33
|
BrowseDirection,
|
|
31
34
|
coerceLocalizedText,
|
|
32
35
|
coerceQualifiedName,
|
|
33
36
|
LocalizedText,
|
|
34
|
-
LocalizedTextLike,
|
|
37
|
+
type LocalizedTextLike,
|
|
35
38
|
makeNodeClassMask,
|
|
36
39
|
NodeClass,
|
|
37
40
|
QualifiedName,
|
|
38
|
-
QualifiedNameLike,
|
|
39
|
-
QualifiedNameOptions
|
|
40
|
-
AccessRestrictionsFlag
|
|
41
|
+
type QualifiedNameLike,
|
|
42
|
+
type QualifiedNameOptions
|
|
41
43
|
} from "node-opcua-data-model";
|
|
42
44
|
import { DataValue } from "node-opcua-data-value";
|
|
43
|
-
import { dumpIf, make_debugLog,
|
|
44
|
-
import { coerceNodeId, makeNodeId, NodeId, NodeIdLike, NodeIdType, resolveNodeId, sameNodeId } from "node-opcua-nodeid";
|
|
45
|
-
import {
|
|
46
|
-
import {
|
|
47
|
-
import {
|
|
45
|
+
import { dumpIf, make_debugLog, make_errorLog, make_warningLog } from "node-opcua-debug";
|
|
46
|
+
import { coerceNodeId, makeNodeId, NodeId, type NodeIdLike, NodeIdType, resolveNodeId, sameNodeId } from "node-opcua-nodeid";
|
|
47
|
+
import type { UAStateVariable } from "node-opcua-nodeset-ua";
|
|
48
|
+
import type { NumericRange } from "node-opcua-numeric-range";
|
|
49
|
+
import type { ReferenceDescription } from "node-opcua-service-browse";
|
|
50
|
+
import { type StatusCode, StatusCodes } from "node-opcua-status-code";
|
|
48
51
|
import {
|
|
49
52
|
PermissionType,
|
|
50
|
-
RelativePathElement,
|
|
53
|
+
type RelativePathElement,
|
|
51
54
|
RolePermissionType,
|
|
52
|
-
RolePermissionTypeOptions,
|
|
53
|
-
WriteValueOptions
|
|
55
|
+
type RolePermissionTypeOptions,
|
|
56
|
+
type WriteValueOptions
|
|
54
57
|
} from "node-opcua-types";
|
|
55
58
|
import { lowerFirstLetter } from "node-opcua-utils";
|
|
56
59
|
import { DataType, VariantArrayType } from "node-opcua-variant";
|
|
57
|
-
|
|
58
|
-
import { UAStateVariable } from "node-opcua-nodeset-ua";
|
|
59
|
-
import { ObjectTypeIds, ReferenceTypeIds, VariableTypeIds } from "node-opcua-constants";
|
|
60
|
-
|
|
61
|
-
import { XmlWriter } from "../source/xml_writer";
|
|
62
60
|
import { dumpReferenceDescriptions, dumpReferences } from "../source/helpers/dump_tools";
|
|
63
61
|
import { SessionContext, WellKnownRolesNodeId } from "../source/session_context";
|
|
64
|
-
import {
|
|
62
|
+
import type { XmlWriter } from "../source/xml_writer";
|
|
63
|
+
import type { AddressSpace } from "../src/address_space";
|
|
65
64
|
import { _handle_add_reference_change_event } from "./address_space_change_event_tools";
|
|
66
|
-
import { AddressSpacePrivate } from "./address_space_private";
|
|
65
|
+
import type { AddressSpacePrivate } from "./address_space_private";
|
|
67
66
|
import {
|
|
68
67
|
_constructReferenceDescription,
|
|
69
|
-
_handle_HierarchicalReference,
|
|
70
68
|
_get_HierarchicalReference,
|
|
69
|
+
_handle_HierarchicalReference,
|
|
71
70
|
_remove_HierarchicalReference,
|
|
72
71
|
BaseNode_add_backward_reference,
|
|
73
|
-
|
|
72
|
+
BaseNode_clearCache,
|
|
73
|
+
BaseNode_getCache,
|
|
74
74
|
BaseNode_getPrivate,
|
|
75
75
|
BaseNode_initPrivate,
|
|
76
|
+
BaseNode_remove_backward_reference,
|
|
76
77
|
BaseNode_removePrivate,
|
|
77
78
|
BaseNode_toString,
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
BaseNode_clearCache,
|
|
81
|
-
HierarchicalIndexMap,
|
|
79
|
+
type HierarchicalIndexMap,
|
|
80
|
+
ToStringBuilder
|
|
82
81
|
} from "./base_node_private";
|
|
83
|
-
import { MinimalistAddressSpace, ReferenceImpl } from "./reference_impl";
|
|
82
|
+
import { type MinimalistAddressSpace, ReferenceImpl } from "./reference_impl";
|
|
84
83
|
import { coerceRolePermissions } from "./role_permissions";
|
|
85
|
-
import { UAString } from "node-opcua-basic-types";
|
|
86
84
|
|
|
85
|
+
type ApplyFunc = { apply: (...args: unknown[]) => void };
|
|
87
86
|
// tslint:disable:no-var-requires
|
|
88
87
|
// tslint:disable:no-bitwise
|
|
89
88
|
// tslint:disable:no-console
|
|
@@ -96,12 +95,12 @@ const debugLog = make_debugLog(__filename);
|
|
|
96
95
|
const HasEventSourceReferenceType = resolveNodeId("HasEventSource");
|
|
97
96
|
const HasNotifierReferenceType = resolveNodeId("HasNotifier");
|
|
98
97
|
|
|
99
|
-
function defaultBrowseFilterFunc(
|
|
98
|
+
function defaultBrowseFilterFunc(_context?: ISessionContext): boolean {
|
|
100
99
|
return true;
|
|
101
100
|
}
|
|
102
101
|
|
|
103
102
|
function _get_QualifiedBrowseName(browseName: QualifiedNameLike): QualifiedName {
|
|
104
|
-
return coerceQualifiedName(browseName)
|
|
103
|
+
return coerceQualifiedName(browseName) || "";
|
|
105
104
|
}
|
|
106
105
|
|
|
107
106
|
export interface InternalBaseNodeOptions {
|
|
@@ -125,7 +124,7 @@ export interface InternalBaseNodeOptions {
|
|
|
125
124
|
rolePermissions?: RolePermissionTypeOptions[];
|
|
126
125
|
}
|
|
127
126
|
|
|
128
|
-
function _is_valid_BrowseDirection(browseDirection:
|
|
127
|
+
function _is_valid_BrowseDirection(browseDirection: BrowseDirection) {
|
|
129
128
|
return (
|
|
130
129
|
browseDirection === BrowseDirection.Forward ||
|
|
131
130
|
browseDirection === BrowseDirection.Inverse ||
|
|
@@ -135,7 +134,7 @@ function _is_valid_BrowseDirection(browseDirection: any) {
|
|
|
135
134
|
|
|
136
135
|
export function makeAttributeEventName(attributeId: AttributeIds): string {
|
|
137
136
|
const attributeName = attributeNameById[attributeId];
|
|
138
|
-
return attributeName
|
|
137
|
+
return `${attributeName}_changed`;
|
|
139
138
|
}
|
|
140
139
|
|
|
141
140
|
/**
|
|
@@ -169,7 +168,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
169
168
|
const _private = BaseNode_getPrivate(this);
|
|
170
169
|
// c8 ignore next
|
|
171
170
|
if (!_private) {
|
|
172
|
-
throw new Error(
|
|
171
|
+
throw new Error(`Internal error , cannot extract private data from ${this.browseName.toString()}`);
|
|
173
172
|
}
|
|
174
173
|
return _private.__address_space as AddressSpace;
|
|
175
174
|
}
|
|
@@ -178,7 +177,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
178
177
|
const _private = BaseNode_getPrivate(this);
|
|
179
178
|
// c8 ignore next
|
|
180
179
|
if (!_private) {
|
|
181
|
-
throw new Error(
|
|
180
|
+
throw new Error(`Internal error , cannot extract private data from ${this.browseName.toString()}`);
|
|
182
181
|
}
|
|
183
182
|
return _private.__address_space as AddressSpacePrivate;
|
|
184
183
|
}
|
|
@@ -190,7 +189,8 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
190
189
|
|
|
191
190
|
public setDisplayName(value: LocalizedTextLike[] | LocalizedTextLike): void {
|
|
192
191
|
if (!Array.isArray(value)) {
|
|
193
|
-
|
|
192
|
+
this.setDisplayName([value]);
|
|
193
|
+
return;
|
|
194
194
|
}
|
|
195
195
|
this._setDisplayName(value);
|
|
196
196
|
/**
|
|
@@ -203,7 +203,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
203
203
|
|
|
204
204
|
public get description(): LocalizedText {
|
|
205
205
|
const _private = BaseNode_getPrivate(this);
|
|
206
|
-
return _private._description
|
|
206
|
+
return _private._description || new LocalizedText({ text: "" });
|
|
207
207
|
}
|
|
208
208
|
|
|
209
209
|
public setDescription(value: LocalizedTextLike | null): void {
|
|
@@ -309,7 +309,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
309
309
|
public readonly nodeId: NodeId;
|
|
310
310
|
public readonly browseName: QualifiedName;
|
|
311
311
|
|
|
312
|
-
protected _postInstantiateFunc?: (instance: BaseNode, instanceType: BaseNode, options?:
|
|
312
|
+
protected _postInstantiateFunc?: (instance: BaseNode, instanceType: BaseNode, options?: unknown) => void;
|
|
313
313
|
|
|
314
314
|
/**
|
|
315
315
|
* @internal
|
|
@@ -339,12 +339,12 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
339
339
|
this.browseName = _get_QualifiedBrowseName(options.browseName);
|
|
340
340
|
|
|
341
341
|
// re-use browseName as displayName if displayName is missing
|
|
342
|
-
options.displayName = options.displayName || this.browseName.name
|
|
342
|
+
options.displayName = options.displayName || this.browseName.name?.toString();
|
|
343
343
|
|
|
344
344
|
if (options.description === undefined) {
|
|
345
345
|
options.description = null;
|
|
346
346
|
}
|
|
347
|
-
this._setDisplayName(options.displayName);
|
|
347
|
+
this._setDisplayName(options.displayName || "");
|
|
348
348
|
|
|
349
349
|
this._setDescription(options.description);
|
|
350
350
|
|
|
@@ -366,9 +366,9 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
366
366
|
this._rolePermissions = coerceRolePermissions(options.rolePermissions);
|
|
367
367
|
}
|
|
368
368
|
|
|
369
|
-
public getDisplayName(
|
|
369
|
+
public getDisplayName(_locale?: string): string {
|
|
370
370
|
const _private = BaseNode_getPrivate(this);
|
|
371
|
-
return _private._displayName[0].text
|
|
371
|
+
return _private._displayName[0].text || "";
|
|
372
372
|
}
|
|
373
373
|
|
|
374
374
|
public get namespace(): INamespace {
|
|
@@ -443,11 +443,11 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
443
443
|
const hash = `r|${referenceTypeNode.nodeId.toString()}|${isForward ? "f" : "b"}`;
|
|
444
444
|
|
|
445
445
|
if (_cache._ref.has(hash)) {
|
|
446
|
-
return _cache._ref.get(hash)
|
|
446
|
+
return _cache._ref.get(hash) || [];
|
|
447
447
|
}
|
|
448
448
|
// c8 ignore next
|
|
449
449
|
if (doDebug && !this.addressSpace.findReferenceType(referenceTypeNode.nodeId)) {
|
|
450
|
-
throw new Error(
|
|
450
|
+
throw new Error(`expecting valid reference name ${referenceType}`);
|
|
451
451
|
}
|
|
452
452
|
const result = this.findReferences_no_cache(referenceTypeNode, isForward);
|
|
453
453
|
_cache._ref.set(hash, result);
|
|
@@ -502,7 +502,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
502
502
|
const _cache = BaseNode_getCache(this);
|
|
503
503
|
if (!_cache._children) {
|
|
504
504
|
_cache._children = this.findReferencesExAsObject(BaseNodeImpl._hasChild, BrowseDirection.Forward);
|
|
505
|
-
}
|
|
505
|
+
}
|
|
506
506
|
return _cache._children;
|
|
507
507
|
}
|
|
508
508
|
|
|
@@ -545,7 +545,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
545
545
|
return null;
|
|
546
546
|
}
|
|
547
547
|
assert(component.nodeClass === NodeClass.Variable || component.nodeClass === NodeClass.Object);
|
|
548
|
-
return component as
|
|
548
|
+
return component as unknown as UAVariable | UAObject;
|
|
549
549
|
} else {
|
|
550
550
|
return null;
|
|
551
551
|
}
|
|
@@ -563,7 +563,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
563
563
|
if (select.length === 1 && select[0].nodeClass !== NodeClass.Variable) {
|
|
564
564
|
throw new Error("Expecting a property to be of nodeClass==NodeClass.Variable");
|
|
565
565
|
}
|
|
566
|
-
return select.length === 1 ? (select[0] as
|
|
566
|
+
return select.length === 1 ? (select[0] as unknown as UAVariable) : null;
|
|
567
567
|
}
|
|
568
568
|
|
|
569
569
|
/**
|
|
@@ -611,7 +611,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
611
611
|
const methods = this.getMethods();
|
|
612
612
|
const select = _filter_by_browse_name(methods, methodName, namespaceIndex);
|
|
613
613
|
assert(select.length <= 1, "BaseNode#getMethodByName found duplicated reference");
|
|
614
|
-
return select.length === 1 ? select[0]
|
|
614
|
+
return select.length === 1 ? select[0] : null;
|
|
615
615
|
}
|
|
616
616
|
|
|
617
617
|
public getWriteMask(): number {
|
|
@@ -630,7 +630,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
630
630
|
indexRange;
|
|
631
631
|
dataEncoding;
|
|
632
632
|
assert(!context || context instanceof SessionContext);
|
|
633
|
-
const options:
|
|
633
|
+
const options: Record<string, unknown> = {};
|
|
634
634
|
options.statusCode = StatusCodes.Good;
|
|
635
635
|
|
|
636
636
|
switch (attributeId) {
|
|
@@ -639,7 +639,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
639
639
|
break;
|
|
640
640
|
|
|
641
641
|
case AttributeIds.NodeClass: // NodeClass
|
|
642
|
-
assert(isFinite(this.nodeClass));
|
|
642
|
+
assert(Number.isFinite(this.nodeClass));
|
|
643
643
|
options.value = { dataType: DataType.Int32, value: this.nodeClass };
|
|
644
644
|
break;
|
|
645
645
|
|
|
@@ -697,10 +697,12 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
697
697
|
writeValue.attributeId <= 0 ||
|
|
698
698
|
writeValue.attributeId > AttributeIds.AccessLevelEx
|
|
699
699
|
) {
|
|
700
|
-
|
|
700
|
+
callback(null, StatusCodes.BadAttributeIdInvalid);
|
|
701
|
+
return;
|
|
701
702
|
}
|
|
702
703
|
if (!this.canUserWriteAttribute(context, writeValue.attributeId)) {
|
|
703
|
-
|
|
704
|
+
callback(null, StatusCodes.BadUserAccessDenied);
|
|
705
|
+
return;
|
|
704
706
|
}
|
|
705
707
|
// by default Node is read-only,
|
|
706
708
|
// this method needs to be overridden to change the behavior
|
|
@@ -713,9 +715,9 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
713
715
|
|
|
714
716
|
// c8 ignore next
|
|
715
717
|
if (parent) {
|
|
716
|
-
return parent.fullName()
|
|
718
|
+
return `${parent.fullName()}.${this.browseName.toString()}`;
|
|
717
719
|
} else {
|
|
718
|
-
return
|
|
720
|
+
return `NOT YET REGISTERED${this.parentNodeId.toString()}.${this.browseName.toString()}`;
|
|
719
721
|
}
|
|
720
722
|
}
|
|
721
723
|
return this.browseName.toString();
|
|
@@ -742,7 +744,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
742
744
|
// The current path cannot be followed any further if no targets with the specified BrowseName exist.
|
|
743
745
|
assert(relativePathElement.targetName instanceof QualifiedName);
|
|
744
746
|
assert(relativePathElement.targetName.namespaceIndex >= 0);
|
|
745
|
-
assert(relativePathElement.targetName.name
|
|
747
|
+
assert((relativePathElement.targetName.name?.length || 0) > 0);
|
|
746
748
|
|
|
747
749
|
// The type of reference to follow from the current node.
|
|
748
750
|
// The current path cannot be followed any further if the referenceTypeId is not available on the Node instance.
|
|
@@ -778,7 +780,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
778
780
|
return true;
|
|
779
781
|
}
|
|
780
782
|
if (relativePathElement.includeSubtypes) {
|
|
781
|
-
const baseType = this.addressSpace.findReferenceType(relativePathElement.referenceTypeId)
|
|
783
|
+
const baseType = this.addressSpace.findReferenceType(relativePathElement.referenceTypeId);
|
|
782
784
|
if (baseType && referenceType.isSubtypeOf(baseType)) {
|
|
783
785
|
return true;
|
|
784
786
|
}
|
|
@@ -786,7 +788,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
786
788
|
return false;
|
|
787
789
|
};
|
|
788
790
|
|
|
789
|
-
const nodeIdsMap:
|
|
791
|
+
const nodeIdsMap: Record<string, BaseNode> = {};
|
|
790
792
|
let nodeIds: NodeId[] = [];
|
|
791
793
|
|
|
792
794
|
for (const reference of references) {
|
|
@@ -798,7 +800,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
798
800
|
|
|
799
801
|
// c8 ignore next
|
|
800
802
|
if (!obj) {
|
|
801
|
-
throw new Error(
|
|
803
|
+
throw new Error(` cannot find node with id ${reference.nodeId.toString()}`);
|
|
802
804
|
}
|
|
803
805
|
|
|
804
806
|
if (isEqual(obj.browseName, relativePathElement.targetName)) {
|
|
@@ -813,11 +815,11 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
813
815
|
}
|
|
814
816
|
|
|
815
817
|
if (nodeIds.length === 0 && (this.nodeClass === NodeClass.ObjectType || this.nodeClass === NodeClass.VariableType)) {
|
|
816
|
-
const nodeType = this as
|
|
818
|
+
const nodeType = this as unknown as UAVariableType;
|
|
817
819
|
|
|
818
820
|
if (nodeType.subtypeOf) {
|
|
819
821
|
// browsing also InstanceDeclarations included in base type
|
|
820
|
-
const baseType = this.addressSpace.findNode(nodeType.subtypeOf)
|
|
822
|
+
const baseType = this.addressSpace.findNode(nodeType.subtypeOf) as BaseNode;
|
|
821
823
|
const n = (baseType as BaseNodeImpl).browseNodeByTargetName(relativePathElement, isLast);
|
|
822
824
|
nodeIds = ([] as NodeId[]).concat(nodeIds, n);
|
|
823
825
|
}
|
|
@@ -833,7 +835,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
833
835
|
*
|
|
834
836
|
*/
|
|
835
837
|
public browseNode(browseDescription: BrowseDescriptionOptions2, context?: ISessionContext): ReferenceDescription[] {
|
|
836
|
-
assert(isFinite(browseDescription.nodeClassMask));
|
|
838
|
+
assert(Number.isFinite(browseDescription.nodeClassMask));
|
|
837
839
|
|
|
838
840
|
const do_debug = false;
|
|
839
841
|
|
|
@@ -898,12 +900,11 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
898
900
|
* myDevice1.addReference({ referenceType: "OrganizedBy", nodeId: view });
|
|
899
901
|
*/
|
|
900
902
|
public addReference(reference: AddReferenceOpts): void {
|
|
901
|
-
|
|
902
903
|
const referenceNode = this.__addReference(reference);
|
|
903
904
|
const addressSpace = this.addressSpace;
|
|
904
905
|
|
|
905
906
|
if (!resolveReferenceType(addressSpace, referenceNode)) {
|
|
906
|
-
throw new Error(
|
|
907
|
+
throw new Error(`BaseNode#addReference : invalid reference ${reference.toString()}`);
|
|
907
908
|
}
|
|
908
909
|
|
|
909
910
|
_propagate_ref.call(this, addressSpace, referenceNode);
|
|
@@ -920,10 +921,15 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
920
921
|
|
|
921
922
|
const addressSpace = this.addressSpace as AddressSpacePrivate;
|
|
922
923
|
|
|
923
|
-
const reference = addressSpace.normalizeReferenceTypes([referenceOpts
|
|
924
|
+
const reference = addressSpace.normalizeReferenceTypes([referenceOpts])?.[0];
|
|
924
925
|
const h = (<ReferenceImpl>reference).hash;
|
|
925
926
|
|
|
926
|
-
const relatedNode = addressSpace.findNode(reference.nodeId)
|
|
927
|
+
const relatedNode = addressSpace.findNode(reference.nodeId);
|
|
928
|
+
|
|
929
|
+
// c8 ignore next
|
|
930
|
+
if (!relatedNode) {
|
|
931
|
+
return;
|
|
932
|
+
}
|
|
927
933
|
|
|
928
934
|
const backwardReference = new ReferenceImpl({
|
|
929
935
|
isForward: !reference.isForward,
|
|
@@ -937,13 +943,11 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
937
943
|
_remove_HierarchicalReference(this, reference);
|
|
938
944
|
this.uninstall_extra_properties(reference);
|
|
939
945
|
this._clear_caches();
|
|
940
|
-
|
|
941
946
|
} else if (_private._back_referenceIdx.has(h)) {
|
|
942
|
-
|
|
947
|
+
relatedNode.removeReference(backwardReference);
|
|
943
948
|
} else {
|
|
944
|
-
warningLog(
|
|
949
|
+
warningLog(`Cannot find reference to remove: ${reference.toString()}`);
|
|
945
950
|
}
|
|
946
|
-
|
|
947
951
|
}
|
|
948
952
|
|
|
949
953
|
/**
|
|
@@ -1002,12 +1006,12 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1002
1006
|
}
|
|
1003
1007
|
const childNode = resolveReferenceNode(addressSpace, reference);
|
|
1004
1008
|
|
|
1005
|
-
const name = lowerFirstLetter(childNode.browseName.name
|
|
1009
|
+
const name = lowerFirstLetter(childNode.browseName.name || "");
|
|
1006
1010
|
if (Object.prototype.hasOwnProperty.call(reservedNames, name)) {
|
|
1007
1011
|
// c8 ignore next
|
|
1008
1012
|
if (doDebug) {
|
|
1009
1013
|
// tslint:disable-next-line:no-console
|
|
1010
|
-
debugLog(chalk.bgWhite.red(
|
|
1014
|
+
debugLog(chalk.bgWhite.red(`Ignoring reserved keyword ${name}`));
|
|
1011
1015
|
}
|
|
1012
1016
|
return;
|
|
1013
1017
|
}
|
|
@@ -1074,12 +1078,11 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1074
1078
|
|
|
1075
1079
|
public getChildByName(browseName: QualifiedNameOptions): BaseNode | null;
|
|
1076
1080
|
public getChildByName(browseName: string, namespaceIndex?: number): BaseNode | null;
|
|
1077
|
-
//
|
|
1081
|
+
//
|
|
1078
1082
|
public getChildByName(browseName: QualifiedNameLike, namespaceIndex?: number): BaseNode | null {
|
|
1079
|
-
|
|
1080
1083
|
var childrenMap = _get_HierarchicalReference(this);
|
|
1081
1084
|
const select = _select_by_browse_name(childrenMap, browseName, namespaceIndex);
|
|
1082
|
-
if (select.length
|
|
1085
|
+
if (select.length === 0) {
|
|
1083
1086
|
return null;
|
|
1084
1087
|
}
|
|
1085
1088
|
const ref = select[0];
|
|
@@ -1090,7 +1093,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1090
1093
|
return null; // too early, bmy be namespace 0 is still loading
|
|
1091
1094
|
}
|
|
1092
1095
|
if (r.isSubtypeOf(hasChild)) {
|
|
1093
|
-
return ref.node
|
|
1096
|
+
return ref.node || null;
|
|
1094
1097
|
}
|
|
1095
1098
|
return null;
|
|
1096
1099
|
}
|
|
@@ -1108,7 +1111,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1108
1111
|
public get nodeVersion(): UAProperty<UAString, DataType.String> | undefined {
|
|
1109
1112
|
return this.getNodeVersion() || undefined;
|
|
1110
1113
|
}
|
|
1111
|
-
public set nodeVersion(
|
|
1114
|
+
public set nodeVersion(_n: unknown) {
|
|
1112
1115
|
assert(false);
|
|
1113
1116
|
}
|
|
1114
1117
|
|
|
@@ -1155,11 +1158,11 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1155
1158
|
this._clear_caches();
|
|
1156
1159
|
|
|
1157
1160
|
const _private = BaseNode_getPrivate(this);
|
|
1158
|
-
for (
|
|
1161
|
+
for (const ref of _private._back_referenceIdx.values()) {
|
|
1159
1162
|
(ref as ReferenceImpl).dispose();
|
|
1160
1163
|
}
|
|
1161
1164
|
|
|
1162
|
-
for (
|
|
1165
|
+
for (const ref of _private._referenceIdx.values()) {
|
|
1163
1166
|
(ref as ReferenceImpl).dispose();
|
|
1164
1167
|
}
|
|
1165
1168
|
|
|
@@ -1172,7 +1175,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1172
1175
|
|
|
1173
1176
|
// c8 ignore next
|
|
1174
1177
|
public dumpXML(xmlWriter: XmlWriter): void {
|
|
1175
|
-
console.error(" This ",
|
|
1178
|
+
console.error(" This ", NodeClass[this.nodeClass]);
|
|
1176
1179
|
assert(false, "BaseNode#dumpXML NOT IMPLEMENTED !");
|
|
1177
1180
|
assert(xmlWriter);
|
|
1178
1181
|
}
|
|
@@ -1209,14 +1212,14 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1209
1212
|
}
|
|
1210
1213
|
}
|
|
1211
1214
|
|
|
1212
|
-
public installPostInstallFunc(f: (instance: BaseNode, tpyeNode: BaseNode, opts?:
|
|
1215
|
+
public installPostInstallFunc(f: (instance: BaseNode, tpyeNode: BaseNode, opts?: unknown) => void): void {
|
|
1213
1216
|
if (!f) {
|
|
1214
1217
|
// nothing to do
|
|
1215
1218
|
return;
|
|
1216
1219
|
}
|
|
1217
1220
|
|
|
1218
|
-
function chain(f1:
|
|
1219
|
-
return function
|
|
1221
|
+
function chain(f1: ApplyFunc | undefined, f2: ApplyFunc | undefined) {
|
|
1222
|
+
return function chainingFunc(this: BaseNode, ...args: unknown[]) {
|
|
1220
1223
|
if (f1) {
|
|
1221
1224
|
f1.apply(this, args);
|
|
1222
1225
|
}
|
|
@@ -1230,7 +1233,6 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1230
1233
|
}
|
|
1231
1234
|
|
|
1232
1235
|
public _on_child_added(childNode: BaseNode): void {
|
|
1233
|
-
|
|
1234
1236
|
// this._clear_caches();
|
|
1235
1237
|
// return;
|
|
1236
1238
|
const cache = BaseNode_getCache(this);
|
|
@@ -1241,11 +1243,11 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1241
1243
|
newCache._versionNode = tmpV;
|
|
1242
1244
|
newCache._children = tmpC;
|
|
1243
1245
|
if (newCache._children) {
|
|
1244
|
-
newCache._children
|
|
1246
|
+
newCache._children?.push(childNode);
|
|
1245
1247
|
}
|
|
1246
1248
|
}
|
|
1247
1249
|
|
|
1248
|
-
public _on_child_removed(
|
|
1250
|
+
public _on_child_removed(_obj: BaseNode): void {
|
|
1249
1251
|
// obj; // unused;
|
|
1250
1252
|
this._clear_caches();
|
|
1251
1253
|
}
|
|
@@ -1259,13 +1261,13 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1259
1261
|
}
|
|
1260
1262
|
|
|
1261
1263
|
protected _coerceReferenceType(referenceType: string | NodeId | UAReferenceType): UAReferenceType | null {
|
|
1262
|
-
let result: UAReferenceType;
|
|
1264
|
+
let result: UAReferenceType | null = null;
|
|
1263
1265
|
if (typeof referenceType === "string") {
|
|
1264
|
-
result = this.addressSpace.findReferenceType(referenceType)
|
|
1266
|
+
result = this.addressSpace.findReferenceType(referenceType);
|
|
1265
1267
|
/* c8 ignore next */
|
|
1266
1268
|
if (!result) {
|
|
1267
1269
|
errorLog("referenceType ", referenceType, " cannot be found");
|
|
1268
|
-
throw new Error(
|
|
1270
|
+
throw new Error(`Cannot coerce reference with name ${referenceType}`);
|
|
1269
1271
|
}
|
|
1270
1272
|
} else if (referenceType instanceof NodeId) {
|
|
1271
1273
|
result = this.addressSpace.findNode(referenceType) as UAReferenceType;
|
|
@@ -1281,7 +1283,6 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1281
1283
|
}
|
|
1282
1284
|
|
|
1283
1285
|
private __addReference(referenceOpts: AddReferenceOpts): UAReference {
|
|
1284
|
-
|
|
1285
1286
|
const addressSpace = this.addressSpace as AddressSpacePrivate;
|
|
1286
1287
|
const _private = BaseNode_getPrivate(this);
|
|
1287
1288
|
assert(Object.prototype.hasOwnProperty.call(referenceOpts, "referenceType"));
|
|
@@ -1311,7 +1312,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1311
1312
|
private _setDescription(description: LocalizedTextLike | null): void {
|
|
1312
1313
|
const __description = coerceLocalizedText(description);
|
|
1313
1314
|
const _private = BaseNode_getPrivate(this);
|
|
1314
|
-
_private._description = __description
|
|
1315
|
+
_private._description = __description || new LocalizedText({ text: "" });
|
|
1315
1316
|
}
|
|
1316
1317
|
|
|
1317
1318
|
private _notifyAttributeChange(attributeId: AttributeIds): void {
|
|
@@ -1339,7 +1340,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1339
1340
|
return context.checkPermission(this, PermissionType.WriteAttribute);
|
|
1340
1341
|
}
|
|
1341
1342
|
|
|
1342
|
-
private _readAccessRestrictions(
|
|
1343
|
+
private _readAccessRestrictions(_context: ISessionContext | null): DataValue {
|
|
1343
1344
|
// https://reference.opcfoundation.org/v104/Core/docs/Part3/8.56/
|
|
1344
1345
|
if (this.accessRestrictions === undefined) {
|
|
1345
1346
|
return new DataValue({ statusCode: StatusCodes.BadAttributeIdInvalid });
|
|
@@ -1373,7 +1374,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1373
1374
|
|
|
1374
1375
|
const rolePermissions = this.rolePermissions.map(({ roleId, permissions }) => {
|
|
1375
1376
|
return new RolePermissionType({
|
|
1376
|
-
roleId: toRoleNodeId(roleId
|
|
1377
|
+
roleId: toRoleNodeId(roleId),
|
|
1377
1378
|
permissions
|
|
1378
1379
|
});
|
|
1379
1380
|
});
|
|
@@ -1411,7 +1412,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1411
1412
|
const rolePermissions = this.rolePermissions
|
|
1412
1413
|
.map(({ roleId, permissions }) => {
|
|
1413
1414
|
return new RolePermissionType({
|
|
1414
|
-
roleId: toRoleNodeId(roleId
|
|
1415
|
+
roleId: toRoleNodeId(roleId),
|
|
1415
1416
|
permissions
|
|
1416
1417
|
});
|
|
1417
1418
|
})
|
|
@@ -1460,7 +1461,7 @@ export class BaseNodeImpl extends EventEmitter implements BaseNode {
|
|
|
1460
1461
|
|
|
1461
1462
|
function toRoleNodeId(s: NodeIdLike): NodeId {
|
|
1462
1463
|
if (typeof s === "string") {
|
|
1463
|
-
return resolveNodeId(WellKnownRolesNodeId[s as
|
|
1464
|
+
return resolveNodeId(WellKnownRolesNodeId[s as keyof typeof WellKnownRolesNodeId]);
|
|
1464
1465
|
}
|
|
1465
1466
|
return coerceNodeId(s);
|
|
1466
1467
|
}
|
|
@@ -1472,7 +1473,7 @@ function toString_ReferenceDescription(ref: UAReference, options: { addressSpace
|
|
|
1472
1473
|
|
|
1473
1474
|
const refNode = addressSpace.findNode(ref.referenceType);
|
|
1474
1475
|
if (!refNode) {
|
|
1475
|
-
return
|
|
1476
|
+
return `Unknown Ref : ${ref}`;
|
|
1476
1477
|
}
|
|
1477
1478
|
const r = new ReferenceImpl({
|
|
1478
1479
|
isForward: ref.isForward,
|
|
@@ -1485,7 +1486,6 @@ function toString_ReferenceDescription(ref: UAReference, options: { addressSpace
|
|
|
1485
1486
|
}
|
|
1486
1487
|
|
|
1487
1488
|
function _setup_parent_item(this: BaseNode, referencesMap: Map<string, UAReference>): BaseNode | null {
|
|
1488
|
-
|
|
1489
1489
|
let references: UAReference[] | MapIterator<UAReference> = referencesMap.values();
|
|
1490
1490
|
|
|
1491
1491
|
const _private = BaseNode_getPrivate(this);
|
|
@@ -1530,19 +1530,12 @@ function toObject(addressSpace: IAddressSpace, reference: UAReference): BaseNode
|
|
|
1530
1530
|
return obj;
|
|
1531
1531
|
}
|
|
1532
1532
|
|
|
1533
|
-
|
|
1534
1533
|
function _asObject<T extends BaseNode>(references: UAReference[], addressSpace: IAddressSpace): T[] {
|
|
1535
|
-
|
|
1536
|
-
return references.map((a) => toObject(addressSpace, a)).filter((o) => o != null && o != undefined) as T[];
|
|
1534
|
+
return references.map((a) => toObject(addressSpace, a)).filter((o) => !!o) as T[];
|
|
1537
1535
|
}
|
|
1538
1536
|
|
|
1539
|
-
function _select_by_browse_name(
|
|
1540
|
-
map: HierarchicalIndexMap,
|
|
1541
|
-
browseName: QualifiedNameLike, namespaceIndex?: number
|
|
1542
|
-
): UAReference[] {
|
|
1543
|
-
|
|
1537
|
+
function _select_by_browse_name(map: HierarchicalIndexMap, browseName: QualifiedNameLike, namespaceIndex?: number): UAReference[] {
|
|
1544
1538
|
if ((namespaceIndex === null || namespaceIndex === undefined) && typeof browseName === "string") {
|
|
1545
|
-
|
|
1546
1539
|
// no namespace specified and needed
|
|
1547
1540
|
const result = map.get(browseName);
|
|
1548
1541
|
if (result) {
|
|
@@ -1551,18 +1544,19 @@ function _select_by_browse_name(
|
|
|
1551
1544
|
}
|
|
1552
1545
|
return [result];
|
|
1553
1546
|
}
|
|
1554
|
-
|
|
1555
1547
|
} else {
|
|
1556
|
-
const _browseName = coerceQualifiedName(
|
|
1557
|
-
|
|
1558
|
-
)
|
|
1548
|
+
const _browseName = coerceQualifiedName(typeof browseName === "string" ? { name: browseName, namespaceIndex } : browseName);
|
|
1549
|
+
// c8 ignore next
|
|
1550
|
+
if (!_browseName) {
|
|
1551
|
+
return [];
|
|
1552
|
+
}
|
|
1559
1553
|
const result = map.get(_browseName.name || "");
|
|
1560
1554
|
if (result) {
|
|
1561
1555
|
if (Array.isArray(result)) {
|
|
1562
1556
|
// only select the one with the matching namepsace index
|
|
1563
|
-
return result.filter((t) => t.node.browseName.namespaceIndex
|
|
1557
|
+
return result.filter((t) => t.node.browseName.namespaceIndex === _browseName.namespaceIndex);
|
|
1564
1558
|
} else {
|
|
1565
|
-
if (result.node.browseName.namespaceIndex
|
|
1559
|
+
if (result.node.browseName.namespaceIndex === _browseName.namespaceIndex) {
|
|
1566
1560
|
return [result];
|
|
1567
1561
|
}
|
|
1568
1562
|
return [];
|
|
@@ -1570,21 +1564,20 @@ function _select_by_browse_name(
|
|
|
1570
1564
|
}
|
|
1571
1565
|
}
|
|
1572
1566
|
return [];
|
|
1573
|
-
|
|
1574
1567
|
}
|
|
1575
1568
|
|
|
1576
1569
|
function _filter_by_browse_name<T extends BaseNode>(components: T[], browseName: QualifiedNameLike, namespaceIndex?: number): T[] {
|
|
1577
1570
|
let select: T[] = [];
|
|
1578
1571
|
if ((namespaceIndex === null || namespaceIndex === undefined) && typeof browseName === "string") {
|
|
1579
|
-
|
|
1580
1572
|
select = components.filter((c: T) => c.browseName.name === browseName);
|
|
1581
1573
|
if (select && select.length > 1) {
|
|
1582
1574
|
warningLog("Multiple children exist with name ", browseName, " please specify a namespace index");
|
|
1583
1575
|
}
|
|
1584
1576
|
} else {
|
|
1585
|
-
const _browseName = coerceQualifiedName(
|
|
1586
|
-
|
|
1587
|
-
|
|
1577
|
+
const _browseName = coerceQualifiedName(typeof browseName === "string" ? { name: browseName, namespaceIndex } : browseName);
|
|
1578
|
+
if (!_browseName) {
|
|
1579
|
+
return [];
|
|
1580
|
+
}
|
|
1588
1581
|
select = components.filter(
|
|
1589
1582
|
(c: T) => c.browseName.name === _browseName.name && c.browseName.namespaceIndex === _browseName.namespaceIndex
|
|
1590
1583
|
);
|
|
@@ -1625,7 +1618,12 @@ function _propagate_ref(this: BaseNode, addressSpace: MinimalistAddressSpace, re
|
|
|
1625
1618
|
// c8 ignore next
|
|
1626
1619
|
if (displayWarningReferencePointingToItSelf) {
|
|
1627
1620
|
// this could happen with method
|
|
1628
|
-
warningLog(
|
|
1621
|
+
warningLog(
|
|
1622
|
+
" Warning: a Reference is pointing to source ",
|
|
1623
|
+
this.nodeId.toString(),
|
|
1624
|
+
this.browseName.toString(),
|
|
1625
|
+
". Is this intentional ?"
|
|
1626
|
+
);
|
|
1629
1627
|
displayWarningReferencePointingToItSelf = false;
|
|
1630
1628
|
}
|
|
1631
1629
|
}
|
|
@@ -1662,7 +1660,7 @@ function normalize_referenceTypeId(addressSpace: IAddressSpace, referenceTypeId?
|
|
|
1662
1660
|
return ref.nodeId;
|
|
1663
1661
|
}
|
|
1664
1662
|
}
|
|
1665
|
-
let nodeId;
|
|
1663
|
+
let nodeId: NodeId;
|
|
1666
1664
|
try {
|
|
1667
1665
|
nodeId = addressSpace.resolveNodeId(referenceTypeId);
|
|
1668
1666
|
} catch (err) {
|
|
@@ -1697,10 +1695,10 @@ function _filter_by_referenceType(
|
|
|
1697
1695
|
}
|
|
1698
1696
|
|
|
1699
1697
|
references = references.filter((reference) => {
|
|
1700
|
-
const ref = resolveReferenceType(this.addressSpace, reference)
|
|
1698
|
+
const ref = resolveReferenceType(this.addressSpace, reference);
|
|
1701
1699
|
// c8 ignore next
|
|
1702
1700
|
if (!ref) {
|
|
1703
|
-
throw new Error(
|
|
1701
|
+
throw new Error(`Cannot find reference type ${reference.toString()}`);
|
|
1704
1702
|
}
|
|
1705
1703
|
// unknown type ... this may happen when the address space is not fully build
|
|
1706
1704
|
assert(ref.nodeClass === NodeClass.ReferenceType);
|
|
@@ -1752,7 +1750,7 @@ function _filter_by_context(node: BaseNode, references: UAReference[], context:
|
|
|
1752
1750
|
}
|
|
1753
1751
|
|
|
1754
1752
|
function _filter_by_nodeClass(this: BaseNode, references: UAReference[], nodeClassMask: number): UAReference[] {
|
|
1755
|
-
assert(isFinite(nodeClassMask));
|
|
1753
|
+
assert(Number.isFinite(nodeClassMask));
|
|
1756
1754
|
if (nodeClassMask === 0) {
|
|
1757
1755
|
return references;
|
|
1758
1756
|
}
|
|
@@ -1821,21 +1819,25 @@ function install_components_as_object_properties(parentObj: BaseNode) {
|
|
|
1821
1819
|
continue;
|
|
1822
1820
|
}
|
|
1823
1821
|
// assumption: we ignore namespace here .
|
|
1824
|
-
const name = lowerFirstLetter(child.browseName.name
|
|
1822
|
+
const name = lowerFirstLetter(child.browseName.name || "");
|
|
1825
1823
|
|
|
1826
1824
|
if (Object.prototype.hasOwnProperty.call(reservedNames, name)) {
|
|
1827
1825
|
// ignore reserved names
|
|
1828
1826
|
if (doDebug) {
|
|
1829
|
-
debugLog(chalk.bgWhite.red(
|
|
1827
|
+
debugLog(chalk.bgWhite.red(`Ignoring reserved keyword ${name}`));
|
|
1830
1828
|
}
|
|
1831
1829
|
continue;
|
|
1832
1830
|
}
|
|
1833
1831
|
|
|
1834
1832
|
// ignore reserved names
|
|
1835
|
-
doDebug && debugLog(
|
|
1833
|
+
doDebug && debugLog(`Installing property ${name}`, " on ", parentObj.browseName.toString());
|
|
1836
1834
|
|
|
1837
1835
|
const hasProperty = Object.prototype.hasOwnProperty.call(parentObj, name);
|
|
1838
|
-
if (
|
|
1836
|
+
if (
|
|
1837
|
+
hasProperty &&
|
|
1838
|
+
(parentObj as unknown as Record<string, unknown>)[name] !== null &&
|
|
1839
|
+
(parentObj as unknown as Record<string, unknown>)[name] !== undefined
|
|
1840
|
+
) {
|
|
1839
1841
|
continue;
|
|
1840
1842
|
}
|
|
1841
1843
|
|
|
@@ -1852,5 +1854,10 @@ function install_components_as_object_properties(parentObj: BaseNode) {
|
|
|
1852
1854
|
}
|
|
1853
1855
|
|
|
1854
1856
|
export function getReferenceType(reference: UAReference): UAReferenceType {
|
|
1855
|
-
|
|
1857
|
+
const r = (reference as ReferenceImpl)._referenceType;
|
|
1858
|
+
// c8 ignore next
|
|
1859
|
+
if (!r) {
|
|
1860
|
+
throw new Error("Internal error : cannot find referenceType");
|
|
1861
|
+
}
|
|
1862
|
+
return r;
|
|
1856
1863
|
}
|