asab_webui_components 25.2.17 → 25.2.19

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.
@@ -6,6 +6,7 @@ Object.defineProperty(exports, "__esModule", {
6
6
  exports.Renderer = void 0;
7
7
  var _react = _interopRequireWildcard(require("react"));
8
8
  var _AsabReactJson = require("../components/AsabReactJson/AsabReactJson.js");
9
+ var _RendererWrapper = require("../components/RendererWrapper/RendererWrapper.js");
9
10
  function _interopRequireWildcard(e, t) { if ("function" == typeof WeakMap) var r = new WeakMap(), n = new WeakMap(); return (_interopRequireWildcard = function _interopRequireWildcard(e, t) { if (!t && e && e.__esModule) return e; var o, i, f = { __proto__: null, default: e }; if (null === e || "object" != typeof e && "function" != typeof e) return f; if (o = t ? n : r) { if (o.has(e)) return o.get(e); o.set(e, f); } for (var _t in e) "default" !== _t && {}.hasOwnProperty.call(e, _t) && ((i = (o = Object.defineProperty) && Object.getOwnPropertyDescriptor(e, _t)) && (i.get || i.set) ? o(f, _t, i) : f[_t] = e[_t]); return f; })(e, t); }
10
11
  class Renderer extends _react.Component {
11
12
  // Renderer defaults
@@ -14,6 +15,7 @@ class Renderer extends _react.Component {
14
15
  this.App = app;
15
16
  }
16
17
  render(key, value, schemaField) {
18
+ var params = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : undefined;
17
19
  // Render ReactJson component if value is a object
18
20
  if (typeof value === 'object') {
19
21
  return /*#__PURE__*/_react.default.createElement(_AsabReactJson.AsabReactJson, {
@@ -27,8 +29,20 @@ class Renderer extends _react.Component {
27
29
  indentWidth: 8
28
30
  });
29
31
  }
32
+
33
+ // Convert bigint to string (to preserve precision and to display the value when no other renderer is applied)
34
+ if (typeof value === "bigint") {
35
+ value = value.toString();
36
+ }
37
+
30
38
  // Render span with value inside as a default
31
- return /*#__PURE__*/_react.default.createElement("span", null, typeof value === "bigint" ? value.toString() : value);
39
+ return /*#__PURE__*/_react.default.createElement(_RendererWrapper.RendererWrapper, {
40
+ "data-value": value // Passing value (to eventually work with in the external wrapper)
41
+ ,
42
+ "data-key": key // Passing key (to eventually work with in the external wrapper)
43
+ ,
44
+ component: (params === null || params === void 0 ? void 0 : params.WrapperComponent) || "span"
45
+ }, value);
32
46
  }
33
47
  plain(key, value, schemaField) {
34
48
  // Render stringified component if value is a object
@@ -40,6 +54,11 @@ class Renderer extends _react.Component {
40
54
  return value;
41
55
  }
42
56
  }
57
+
58
+ // Convert bigint to string (to preserve precision and to display the value when no other renderer is applied)
59
+ if (typeof value === "bigint") {
60
+ value = value.toString();
61
+ }
43
62
  return value;
44
63
  }
45
64
  }
@@ -0,0 +1,19 @@
1
+ "use strict";
2
+
3
+ var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
4
+ Object.defineProperty(exports, "__esModule", {
5
+ value: true
6
+ });
7
+ exports.RendererWrapper = RendererWrapper;
8
+ var _objectWithoutProperties2 = _interopRequireDefault(require("@babel/runtime/helpers/objectWithoutProperties"));
9
+ var _react = _interopRequireDefault(require("react"));
10
+ var _excluded = ["children", "component"];
11
+ // Renderer wraper
12
+ function RendererWrapper(_ref) {
13
+ var {
14
+ children,
15
+ component: Component = 'span' // Default tag, can be overloaded
16
+ } = _ref,
17
+ rest = (0, _objectWithoutProperties2.default)(_ref, _excluded);
18
+ return /*#__PURE__*/_react.default.createElement(Component, rest, children);
19
+ }
@@ -0,0 +1,16 @@
1
+ import React from 'react';
2
+
3
+ // Renderer wraper
4
+ export function RendererWrapper({
5
+ children,
6
+ component: Component = 'span', // Default tag, can be overloaded
7
+ ...rest
8
+ }) {
9
+ return (
10
+ <Component
11
+ {...rest}
12
+ >
13
+ {children}
14
+ </Component>
15
+ );
16
+ }
package/dist/index.js CHANGED
@@ -172,6 +172,12 @@ Object.defineProperty(exports, "Renderer", {
172
172
  return _Renderer.Renderer;
173
173
  }
174
174
  });
175
+ Object.defineProperty(exports, "RendererWrapper", {
176
+ enumerable: true,
177
+ get: function get() {
178
+ return _RendererWrapper.RendererWrapper;
179
+ }
180
+ });
175
181
  Object.defineProperty(exports, "ResultCard", {
176
182
  enumerable: true,
177
183
  get: function get() {
@@ -381,6 +387,7 @@ var _FullscreenButton = require("./components/FullscreenButton.js");
381
387
  var _ConsoleCard = require("./components/Console/ConsoleCard.js");
382
388
  var _isoCodeCountries = require("./utils/lookups/isoCodeCountries.js");
383
389
  var _AttentionRequiredBadge = require("./components/AttentionRequired/AttentionRequiredBadge.js");
390
+ var _RendererWrapper = require("./components/RendererWrapper/RendererWrapper.js");
384
391
  require("./styles/index.scss");
385
392
  var _Pagination = _interopRequireDefault(require("./components/DataTable/Pagination"));
386
393
  var _DataTable2 = require("./components/DataTable");
@@ -46,11 +46,14 @@
46
46
  --slate-smoke: #6a6a6a8f; // The color of the disabled item text in the TreeMenu
47
47
  --slate-smoke-rgb: 106, 106, 106;
48
48
 
49
- --deep-red: #D1004A; // The color of the highest Alert severity
50
- --deep-red-rgb: 209, 0, 74;
49
+ --light-honey: #ffe082; // The color of the lowest Alert severity
50
+ --light-honey-rgb: 255, 224, 130;
51
51
 
52
- --deep-green: #0E6027; // The color of the lowest Alert severity
53
- --deep-green-rgb: 14, 96, 39;
52
+ --bright-orange: #ff9800; // The color of the medium Alert severity
53
+ --bright-orange-rgb: 255, 125, 0;
54
+
55
+ --fiery-sunset: #ff5722; // The color of the high Alert severity
56
+ --fiery-sunset-rgb: 255, 87, 34;
54
57
 
55
58
  --charcoal: #494949; // Console background dark theme
56
59
  --charcoal-rgb: 0, 43, 54;
@@ -63,10 +66,4 @@
63
66
 
64
67
  --moody-blues: #586E75; // Console font color for light theme
65
68
  --moody-blues-rgb: rgb(88, 110, 117);
66
-
67
- --soft-gray: #e1e2e7; // Emulate table hover row color for light theme
68
- --soft-gray-rgb: rgb(225, 226, 231);
69
-
70
- --charcoal-blue: #202636; // Emulate table hover row color for dark theme
71
- --charcoal-blue-rgb: rgb(32, 38, 54);
72
69
  }
@@ -1,30 +1,72 @@
1
1
  "use strict";
2
2
 
3
+ var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
3
4
  Object.defineProperty(exports, "__esModule", {
4
5
  value: true
5
6
  });
6
7
  exports.classifyIPAddress = classifyIPAddress;
8
+ var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty"));
9
+ function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
10
+ function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { (0, _defineProperty2.default)(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
7
11
  function parseIPv4(ipAddress) {
8
- var ipv4Octets = ipAddress.split('.'); // Octet is on of the segments of an IP address
9
- if (ipv4Octets.length == 4) {
10
- return ipv4Octets.reduce((acc, octet) => (acc << 8n) + BigInt(octet), 0n);
12
+ if (typeof ipAddress == 'string') {
13
+ var ipv4Octets = ipAddress.split('.'); // Octet is on of the segments of an IP address
14
+ if (ipv4Octets.length == 4) {
15
+ return ipv4Octets.reduce((acc, octet) => (acc << 8n) + BigInt(octet), 0n);
16
+ } else {
17
+ return undefined;
18
+ }
19
+ }
20
+ var bigintIP4Address = undefined;
21
+ if (typeof ipAddress === 'bigint') {
22
+ bigintIP4Address = ipAddress;
23
+ } else if (typeof ipAddress === 'object' && 'h' in ipAddress && 'l' in ipAddress) {
24
+ // This part can be removed in Jan 2026 when object form of IP address is removed from the codebase
25
+ bigintIP4Address = (BigInt(ipAddress.h) << 64n) + BigInt(ipAddress.l);
26
+ } else if (typeof ipAddress === 'number') {
27
+ bigintIP4Address = BigInt(ipAddress);
28
+ }
29
+ if (bigintIP4Address !== undefined) {
30
+ // Check if the address is in the ::ffff:0:0/96 range (IPv4-mapped IPv6 addresses) - then it is an IPv4 address
31
+ var ipv4MappedPrefix = BigInt('0x0000000000000000FFFF00000000');
32
+ var ipv4Mask = BigInt('0xFFFFFFFF');
33
+ if ((bigintIP4Address & BigInt('0xFFFFFFFFFFFFFFFFFFFF00000000')) === ipv4MappedPrefix) {
34
+ return bigintIP4Address & ipv4Mask;
35
+ }
36
+
37
+ // Check if the address is in the ::/96 range - then it is an IPv4 address
38
+ var ipv6Prefix = BigInt('0x00000000000000000000000000000000');
39
+ if ((bigintIP4Address & BigInt('0xFFFFFFFFFFFFFFFFFFFFFFFF00000000')) === ipv6Prefix) {
40
+ return bigintIP4Address;
41
+ }
11
42
  }
12
43
  return undefined;
13
44
  }
14
45
  function parseIPv6(ipAddress) {
15
- var ipv6Address = ipAddress;
16
- if (ipv6Address.includes('::')) {
17
- var parts = ipv6Address.split('::');
18
- var left = parts[0] ? parts[0].split(':') : [];
19
- var right = parts[1] ? parts[1].split(':') : [];
20
- var missing = 8 - (left.length + right.length);
21
- var zeros = Array(missing).fill('0000');
22
- var full = [...left, ...zeros, ...right];
23
- ipv6Address = full.map(block => block.padStart(4, '0')).join(':');
24
- }
25
- var ipv6Blocks = ipv6Address.split(':'); // Block is on of the segments of an IP address
26
- if (ipv6Blocks.length == 8) {
27
- return ipv6Blocks.reduce((acc, block) => (acc << 16n) + BigInt(parseInt(block, 16)), 0n);
46
+ if (typeof ipAddress == 'string') {
47
+ var ipv6Address = ipAddress;
48
+ if (ipv6Address.includes('::')) {
49
+ var parts = ipv6Address.split('::');
50
+ var left = parts[0] ? parts[0].split(':') : [];
51
+ var right = parts[1] ? parts[1].split(':') : [];
52
+ var missing = 8 - (left.length + right.length);
53
+ var zeros = Array(missing).fill('0000');
54
+ var full = [...left, ...zeros, ...right];
55
+ ipv6Address = full.map(block => block.padStart(4, '0')).join(':');
56
+ }
57
+ var ipv6Blocks = ipv6Address.split(':'); // Block is on of the segments of an IP address
58
+ if (ipv6Blocks.length == 8) {
59
+ return ipv6Blocks.reduce((acc, block) => (acc << 16n) + BigInt(parseInt(block, 16)), 0n);
60
+ } else {
61
+ return undefined;
62
+ }
63
+ } else if (typeof ipAddress === 'bigint') {
64
+ return ipAddress;
65
+ } else if (typeof ipAddress === 'object' && 'h' in ipAddress && 'l' in ipAddress) {
66
+ // This part can be removed in Jan 2026 when object form of IP address is removed from the codebase
67
+ return (BigInt(ipAddress.h) << 64n) + BigInt(ipAddress.l);
68
+ } else if (typeof ipAddress === 'number') {
69
+ return BigInt(ipAddress);
28
70
  }
29
71
  return undefined;
30
72
  }
@@ -36,120 +78,254 @@ function parseIPv6(ipAddress) {
36
78
  var ipv4Ranges = [{
37
79
  block: parseIPv4("10.0.0.0"),
38
80
  mask: 8,
39
- class: "IPv4 private"
81
+ attrs: {
82
+ cls: "private",
83
+ family: "IPv4",
84
+ msg: "IPv4 private"
85
+ }
40
86
  }, {
41
87
  block: parseIPv4("172.16.0.0"),
42
88
  mask: 12,
43
- class: "IPv4 private" // https://datatracker.ietf.org/doc/html/rfc1918
89
+ // https://datatracker.ietf.org/doc/html/rfc1918
90
+ attrs: {
91
+ cls: "private",
92
+ family: "IPv4",
93
+ msg: "IPv4 private"
94
+ }
44
95
  }, {
45
96
  block: parseIPv4("192.168.0.0"),
46
97
  mask: 16,
47
- class: "IPv4 private"
98
+ attrs: {
99
+ cls: "private",
100
+ family: "IPv4",
101
+ msg: "IPv4 private"
102
+ }
48
103
  }, {
49
104
  block: parseIPv4("169.254.0.0"),
50
105
  mask: 24,
51
- class: "IPv4 reserved"
106
+ attrs: {
107
+ cls: "special",
108
+ family: "IPv4",
109
+ msg: "IPv4 reserved"
110
+ }
52
111
  }, {
53
112
  block: parseIPv4("169.254.255.0"),
54
113
  mask: 24,
55
- class: "IPv4 reserved"
114
+ attrs: {
115
+ cls: "special",
116
+ family: "IPv4",
117
+ msg: "IPv4 reserved"
118
+ }
56
119
  }, {
57
120
  block: parseIPv4("169.254.0.0"),
58
121
  mask: 16,
59
- class: "IPv4 link-local" // https://datatracker.ietf.org/doc/html/rfc3927
122
+ // https://datatracker.ietf.org/doc/html/rfc3927
123
+ attrs: {
124
+ cls: "special",
125
+ family: "IPv4",
126
+ msg: "IPv4 link-local"
127
+ }
60
128
  }, {
61
129
  block: parseIPv4("100.64.0.0"),
62
130
  mask: 10,
63
- class: "IPv4 SAS" // Shared Address Space https://datatracker.ietf.org/doc/html/rfc6598
131
+ // Shared Address Space https://datatracker.ietf.org/doc/html/rfc6598
132
+ attrs: {
133
+ cls: "special",
134
+ family: "IPv4",
135
+ msg: "IPv4 Shared Address Space"
136
+ }
64
137
  }, {
65
138
  block: parseIPv4("127.0.0.0"),
66
139
  mask: 8,
67
- class: "IPv4 loopback"
140
+ attrs: {
141
+ cls: "special",
142
+ family: "IPv4",
143
+ msg: "IPv4 loopback"
144
+ }
68
145
  }, {
69
146
  block: parseIPv4("0.0.0.0"),
70
147
  mask: 8,
71
- class: "IPv4 special"
148
+ attrs: {
149
+ cls: "special",
150
+ family: "IPv4",
151
+ msg: "IPv4 reserved"
152
+ }
72
153
  }, {
73
154
  block: parseIPv4("192.0.0.0"),
74
155
  mask: 29,
75
- class: "IPv4 ds-lite" // https://datatracker.ietf.org/doc/html/rfc6333
156
+ attrs: {
157
+ cls: "special",
158
+ family: "IPv4",
159
+ msg: "IPv4 ds-lite"
160
+ }
76
161
  }, {
77
162
  block: parseIPv4("192.0.2.0"),
78
163
  mask: 24,
79
- class: "IPv4 documentation" // https://datatracker.ietf.org/doc/html/rfc5737
164
+ // https://datatracker.ietf.org/doc/html/rfc5737
165
+ attrs: {
166
+ cls: "special",
167
+ family: "IPv4",
168
+ msg: "IPv4 documentation"
169
+ }
80
170
  }, {
81
171
  block: parseIPv4("192.88.99.0"),
82
172
  mask: 24,
83
- class: "IPv4 6to4" // RFC3068
173
+ // RFC3068
174
+ attrs: {
175
+ cls: "special",
176
+ family: "IPv4",
177
+ msg: "IPv4 6to4"
178
+ }
84
179
  }, {
85
180
  block: parseIPv4("198.18.0.0"),
86
181
  mask: 15,
87
- class: "IPv4 benchmarking" // https://datatracker.ietf.org/doc/html/rfc2544
182
+ attrs: {
183
+ cls: "special",
184
+ family: "IPv4",
185
+ msg: "IPv4 benchmarking"
186
+ }
88
187
  }, {
89
188
  block: parseIPv4("198.51.100.0"),
90
189
  mask: 24,
91
- class: "IPv4 documentation" // https://datatracker.ietf.org/doc/html/rfc5737
190
+ // https://datatracker.ietf.org/doc/html/rfc5737
191
+ attrs: {
192
+ cls: "special",
193
+ family: "IPv4",
194
+ msg: "IPv4 documentation"
195
+ }
92
196
  }, {
93
197
  block: parseIPv4("203.0.113.0"),
94
198
  mask: 24,
95
- class: "IPv4 documentation" // https://datatracker.ietf.org/doc/html/rfc5737
199
+ // https://datatracker.ietf.org/doc/html/rfc5737
200
+ attrs: {
201
+ cls: "special",
202
+ family: "IPv4",
203
+ msg: "IPv4 documentation"
204
+ }
96
205
  }, {
97
206
  block: parseIPv4("240.0.0.0"),
98
207
  mask: 4,
99
- class: "IPv4 reserved" // [RFC1112], Section 4
208
+ // [RFC1112], Section 4
209
+ attrs: {
210
+ cls: "special",
211
+ family: "IPv4",
212
+ msg: "IPv4 reserved"
213
+ }
100
214
  }, {
101
215
  block: parseIPv4("255.255.255.255"),
102
216
  mask: 32,
103
- class: "IPv4 limited-broadcast" // RFC0919], Section 7
217
+ attrs: {
218
+ cls: "special",
219
+ family: "IPv4",
220
+ msg: "IPv4 limited-broadcast"
221
+ }
104
222
  }];
105
223
  var ipv6Ranges = [{
106
224
  block: parseIPv6("::1"),
107
225
  mask: 128,
108
- class: "IPv6 loopback" // https://datatracker.ietf.org/doc/html/rfc4291
226
+ // https://datatracker.ietf.org/doc/html/rfc4291
227
+ attrs: {
228
+ cls: "special",
229
+ family: "IPv6",
230
+ msg: "IPv6 loopback"
231
+ }
109
232
  }, {
110
233
  block: parseIPv6("::"),
111
234
  mask: 128,
112
- class: "IPv6 unspecified" // https://datatracker.ietf.org/doc/html/rfc4291
235
+ // https://datatracker.ietf.org/doc/html/rfc4291
236
+ attrs: {
237
+ cls: "special",
238
+ family: "IPv6",
239
+ msg: "IPv6 unspecified"
240
+ }
113
241
  }, {
114
242
  block: parseIPv6("64:ff9b::"),
115
243
  mask: 96,
116
- class: "IPv6 IPv4-IPv6" // https://datatracker.ietf.org/doc/html/rfc6052
244
+ // https://datatracker.ietf.org/doc/html/rfc6052
245
+ attrs: {
246
+ cls: "special",
247
+ family: "IPv6",
248
+ msg: "IPv6 IPv4-IPv6"
249
+ }
117
250
  }, {
118
251
  block: parseIPv6("::ffff:0:0"),
119
252
  mask: 96,
120
- class: "IPv6 IPv4-mapped" // https://datatracker.ietf.org/doc/html/rfc4291
253
+ attrs: {
254
+ cls: "special",
255
+ family: "IPv6",
256
+ msg: "IPv6 IPv4-mapped"
257
+ }
121
258
  }, {
122
259
  block: parseIPv6("100::"),
123
260
  mask: 64,
124
- class: "IPv6 discard" // https://datatracker.ietf.org/doc/html/rfc6666
261
+ // https://datatracker.ietf.org/doc/html/rfc6666
262
+ attrs: {
263
+ cls: "special",
264
+ family: "IPv6",
265
+ msg: "IPv6 discard"
266
+ }
125
267
  }, {
126
268
  block: parseIPv6("2001::"),
127
269
  mask: 32,
128
- class: "IPv6 terredo" // https://datatracker.ietf.org/doc/html/rfc4380
270
+ // https://datatracker.ietf.org/doc/html/rfc4380
271
+ attrs: {
272
+ cls: "special",
273
+ family: "IPv6",
274
+ msg: "IPv6 terredo"
275
+ }
129
276
  }, {
130
277
  block: parseIPv6("2001:2::"),
131
278
  mask: 32,
132
- class: "IPv6 benchmarking" // https://datatracker.ietf.org/doc/html/rfc5180
279
+ // https://datatracker.ietf.org/doc/html/rfc5180
280
+ attrs: {
281
+ cls: "special",
282
+ family: "IPv6",
283
+ msg: "IPv6 benchmarking"
284
+ }
133
285
  }, {
134
286
  block: parseIPv6("2001:db8::"),
135
287
  mask: 32,
136
- class: "IPv6 documentation" // https://datatracker.ietf.org/doc/html/rfc3849
288
+ // https://datatracker.ietf.org/doc/html/rfc3849
289
+ attrs: {
290
+ cls: "special",
291
+ family: "IPv6",
292
+ msg: "IPv6 documentation"
293
+ }
137
294
  }, {
138
295
  block: parseIPv6("2001:10::"),
139
296
  mask: 28,
140
- class: "IPv6 orchid" // https://datatracker.ietf.org/doc/html/rfc4843
297
+ // https://datatracker.ietf.org/doc/html/rfc4843
298
+ attrs: {
299
+ cls: "special",
300
+ family: "IPv6",
301
+ msg: "IPv6 orchid"
302
+ }
141
303
  }, {
142
304
  block: parseIPv6("2002::"),
143
305
  mask: 16,
144
- class: "IPv6 6to4" // https://datatracker.ietf.org/doc/html/rfc3056
306
+ // https://datatracker.ietf.org/doc/html/rfc3056
307
+ attrs: {
308
+ cls: "special",
309
+ family: "IPv6",
310
+ msg: "IPv6 6to4"
311
+ }
145
312
  }, {
146
313
  block: parseIPv6("fc00::"),
147
314
  mask: 7,
148
- class: "IPv6 private" // https://datatracker.ietf.org/doc/html/rfc4193
315
+ // https://datatracker.ietf.org/doc/html/rfc4193
316
+ attrs: {
317
+ cls: "private",
318
+ family: "IPv6",
319
+ msg: "IPv6 unique local"
320
+ }
149
321
  }, {
150
322
  block: parseIPv6("fe80::"),
151
323
  mask: 10,
152
- class: "IPv6 link-local" // https://datatracker.ietf.org/doc/html/rfc4291
324
+ attrs: {
325
+ cls: "special",
326
+ family: "IPv6",
327
+ msg: "IPv6 link-local"
328
+ }
153
329
  }];
154
330
  function classifyIPv4(ipAddress) {
155
331
  for (var range of ipv4Ranges) {
@@ -157,10 +333,17 @@ function classifyIPv4(ipAddress) {
157
333
  var network = range.block & ~mask;
158
334
  var ipNetwork = ipAddress & ~mask;
159
335
  if (network === ipNetwork) {
160
- return range.class;
336
+ return _objectSpread(_objectSpread({}, range.attrs), {}, {
337
+ normalizedValue: stringifyIPv4(ipAddress)
338
+ });
161
339
  }
162
340
  }
163
- return "IPv4 public"; // If no range matches, it's a public IP
341
+ return {
342
+ cls: "public",
343
+ family: "IPv4",
344
+ normalizedValue: stringifyIPv4(ipAddress),
345
+ msg: "IPv4 public"
346
+ };
164
347
  }
165
348
  function classifyIPv6(ipAddress) {
166
349
  for (var range of ipv6Ranges) {
@@ -168,44 +351,49 @@ function classifyIPv6(ipAddress) {
168
351
  var network = range.block & ~mask;
169
352
  var ipNetwork = ipAddress & ~mask;
170
353
  if (network === ipNetwork) {
171
- return range.class;
354
+ return _objectSpread(_objectSpread({}, range.attrs), {}, {
355
+ normalizedValue: stringifyIPv6(ipAddress)
356
+ });
172
357
  }
173
358
  }
174
- return "IPv6 public"; // If no range matches, it's a public IP
359
+ return {
360
+ cls: "public",
361
+ family: "IPv6",
362
+ normalizedValue: stringifyIPv6(ipAddress),
363
+ msg: "IPv6 public"
364
+ };
175
365
  }
176
366
 
177
367
  /*
178
368
  Classify an IP address.
179
369
  Input:
180
- ipAddress - string, IP address to classify
370
+ ipAddress - string/BigInt/object{h: number, l: number}, IP address to classify
181
371
 
182
372
  Returns:
183
- "IPv4 private"
184
- "IPv4 public"
185
- "IPv4 ..."
186
- "IPv6 private"
187
- "IPv6 public"
188
- "IPv6 ..."
189
- "invalid" ... for invalid IP address
190
- "invalid parse ipv4" ... for invalid IPv4 address
191
- "invalid parse ipv6" ... for invalid IPv6 address
192
-
193
- The first word is "IPv4", "IPv6" or "invalid".
194
-
195
- If the second word is "private", it means that the IP address is private.
196
- If the second word is "public", it means that the IP address is public.
197
- Any other second word means "special".
373
+ Dictionary
198
374
  */
199
375
 
200
376
  function classifyIPAddress(ipAddress) {
201
377
  var ipv4 = undefined;
202
378
  var ipv6 = undefined;
379
+ if (ipAddress == undefined) {
380
+ return {
381
+ cls: "invalid",
382
+ normalizedValue: "N/A",
383
+ msg: "Not an IP address"
384
+ };
385
+ }
203
386
 
204
387
  // Parse IPv4 address
205
388
  try {
206
389
  ipv4 = parseIPv4(ipAddress);
207
390
  } catch (error) {
208
- return "invalid parse ipv4";
391
+ console.error(error);
392
+ return {
393
+ cls: "invalid",
394
+ normalizedValue: sanitizeInvalidIPAddress(ipAddress),
395
+ msg: "invalid parse ipv4"
396
+ };
209
397
  }
210
398
  if (ipv4 !== undefined) {
211
399
  return classifyIPv4(ipv4);
@@ -215,10 +403,88 @@ function classifyIPAddress(ipAddress) {
215
403
  try {
216
404
  ipv6 = parseIPv6(ipAddress);
217
405
  } catch (error) {
218
- return "invalid parse ipv6";
406
+ return {
407
+ cls: "invalid",
408
+ normalizedValue: sanitizeInvalidIPAddress(ipAddress),
409
+ msg: "invalid parse ipv6"
410
+ };
219
411
  }
220
412
  if (ipv6 !== undefined) {
221
413
  return classifyIPv6(ipv6);
222
414
  }
223
- return "invalid"; // Means invalid IP address
224
- }
415
+ return {
416
+ cls: "invalid",
417
+ normalizedValue: sanitizeInvalidIPAddress(ipAddress),
418
+ msg: "Not an IP address"
419
+ };
420
+ }
421
+
422
+ // Improved function to compress IPv6 addresses, fully replicating Python's `.compressed` behavior.
423
+ var stringifyIPv6 = bigintIP6Address => {
424
+ var parts = [];
425
+ for (var i = 0; i < 8; i++) {
426
+ parts.unshift(Number(bigintIP6Address & 0xFFFFn).toString(16));
427
+ bigintIP6Address >>= 16n;
428
+ }
429
+
430
+ // Variables to track the start and length of the longest sequence of zeros.
431
+ var zeroStart = -1; // Start index of the longest zero sequence
432
+ var zeroMax = 0; // Length of the longest zero sequence
433
+ var zeroTempStart = -1; // Start index of the current zero sequence being checked
434
+ var zeroTempLen = 0; // Length of the current zero sequence being checked
435
+
436
+ // Iterate through the parts of the IPv6 address to find the longest sequence of zeros.
437
+ for (var _i = 0; _i < parts.length; _i++) {
438
+ if (parts[_i] === '0') {
439
+ // If the current part is zero, start or continue tracking a zero sequence.
440
+ if (zeroTempStart === -1) zeroTempStart = _i; // Mark the start of the sequence
441
+ zeroTempLen++; // Increment the length of the current sequence
442
+ } else {
443
+ // If the current part is not zero, check if the current zero sequence is the longest.
444
+ if (zeroTempLen > zeroMax) {
445
+ zeroStart = zeroTempStart; // Update the start of the longest sequence
446
+ zeroMax = zeroTempLen; // Update the length of the longest sequence
447
+ }
448
+ // Reset the tracking variables for the next potential zero sequence.
449
+ zeroTempStart = -1;
450
+ zeroTempLen = 0;
451
+ }
452
+ }
453
+
454
+ // After the loop, check if the last zero sequence is the longest.
455
+ if (zeroTempLen > zeroMax) {
456
+ zeroStart = zeroTempStart;
457
+ zeroMax = zeroTempLen;
458
+ }
459
+
460
+ // If a sequence of more than one zero is found, replace it with `::` to compress the IPv6 address.
461
+ if (zeroMax > 1) {
462
+ parts.splice(zeroStart, zeroMax, ''); // Replace the zero sequence with an empty string
463
+ }
464
+
465
+ // Join the parts with colons to form the final compressed IPv6 address.
466
+ return parts.join(':');
467
+ };
468
+ var stringifyIPv4 = bigintIP4Address => {
469
+ var parts = [];
470
+ for (var i = 0; i < 4; i++) {
471
+ parts.push(Number(bigintIP4Address & 0xFFn));
472
+ bigintIP4Address >>= 8n;
473
+ }
474
+ return parts.reverse().join('.');
475
+ };
476
+
477
+ // This function is used to sanitize the input which is NOT the IP address to a string.
478
+ var sanitizeInvalidIPAddress = ipAddress => {
479
+ if (typeof ipAddress === 'string') {
480
+ return ipAddress;
481
+ } else if (typeof ipAddress === 'bigint') {
482
+ return ipAddress.toString();
483
+ } else if (typeof ipAddress === 'object') {
484
+ return "".concat(ipAddress); // TODO: This can be more clever if needed
485
+ } else if (typeof ipAddress === 'number') {
486
+ return ipAddress.toString();
487
+ } else {
488
+ return "???";
489
+ }
490
+ };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "asab_webui_components",
3
- "version": "25.2.17",
3
+ "version": "25.2.19",
4
4
  "license": "BSD-3-Clause",
5
5
  "description": "TeskaLabs ASAB WebUI Components Library",
6
6
  "contributors": [