net-snmp 3.12.1 → 3.13.1

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/.travis.yml CHANGED
@@ -1,6 +1,9 @@
1
1
  language: node_js
2
2
  node_js:
3
3
  - lts/*
4
+ - 20
5
+ - 18
6
+ - 16
4
7
  - 14
5
8
  - 12
6
9
  - 10
package/README.md CHANGED
@@ -1554,9 +1554,12 @@ in the `rinfo` field. For example:
1554
1554
  Returns the receiver's `Authorizer` instance, used to control access
1555
1555
  to the receiver. See the `Authorizer` section for further details.
1556
1556
 
1557
- ## receiver.close ()
1557
+ ## receiver.close (callback)
1558
1558
 
1559
- Closes the receiver's listening socket, ending the operation of the receiver.
1559
+ Closes the receiver's listening socket(s), ending the operation of the receiver. The optionnal
1560
+ `callback` parameter is a callback function of the form `function (socket)`, which will be
1561
+ called once for each socket that the receiver is listening on, after the socket is closed.
1562
+ The `socket` argument will be given as an object triple of `address`, `family` and `port`.
1560
1563
 
1561
1564
  # Application: SNMP Agent
1562
1565
 
@@ -1657,9 +1660,12 @@ its existing `Mib` instance.
1657
1660
  Returns the agent's singleton `Forwarder` instance, which holds a list of registered
1658
1661
  proxies that specify context-based forwarding to remote hosts.
1659
1662
 
1660
- ## agent.close ()
1663
+ ## agent.close (callback)
1661
1664
 
1662
- Closes the agent's listening socket, ending the operation of the agent.
1665
+ Closes the agent's listening socket(s), ending the operation of the agent. The optionnal
1666
+ `callback` parameter is a callback function of the form `function (socket)`, which will be
1667
+ called once for each socket that the agent is listening on, after the socket is closed.
1668
+ The `socket` argument will be given as an object triple of `address`, `family` and `port`.
1663
1669
 
1664
1670
  # Authorizer Module
1665
1671
 
@@ -3385,6 +3391,14 @@ Example programs are included under the module's `example` directory.
3385
3391
 
3386
3392
  * Fix SNMPv1 session walk infinite loop condition
3387
3393
 
3394
+ ## Version 3.13.0 - 03/09/2024
3395
+
3396
+ * Add support for out-of-order MIB dependencies
3397
+
3398
+ ## Version 3.13.1 - 03/09/2024
3399
+
3400
+ * Add close callback for agent and receiver
3401
+
3388
3402
  # License
3389
3403
 
3390
3404
  Copyright (c) 2020 Mark Abrahams <mark@abrahams.co.nz>
@@ -0,0 +1,95 @@
1
+ module.exports = [
2
+ {
3
+ files: ['**/*.js'],
4
+ languageOptions: {
5
+ ecmaVersion: 2020,
6
+ sourceType: 'module',
7
+ globals: {
8
+ // Browser globals
9
+ window: 'readonly',
10
+ document: 'readonly',
11
+ navigator: 'readonly',
12
+
13
+ // Node.js globals
14
+ require: 'readonly',
15
+ module: 'readonly',
16
+ process: 'readonly',
17
+ __dirname: 'readonly',
18
+ __filename: 'readonly',
19
+ console: 'readonly',
20
+ exports: 'readonly',
21
+ Buffer: 'readonly',
22
+ setInterval: 'readonly',
23
+ setTimeout: 'readonly',
24
+ clearInterval: 'readonly',
25
+ clearTimeout: 'readonly',
26
+
27
+ // Mocha globals
28
+ describe: 'readonly',
29
+ it: 'readonly',
30
+ before: 'readonly',
31
+ after: 'readonly',
32
+ beforeEach: 'readonly',
33
+ afterEach: 'readonly',
34
+
35
+ // ES6 globals
36
+ Promise: 'readonly',
37
+ Set: 'readonly',
38
+ Map: 'readonly',
39
+
40
+ // User-defined globals
41
+ $: 'readonly',
42
+ System: 'readonly',
43
+ expect: 'readonly',
44
+ },
45
+ },
46
+ linterOptions: {
47
+ reportUnusedDisableDirectives: true,
48
+ },
49
+ rules: {
50
+ 'accessor-pairs': 'error',
51
+ 'arrow-spacing': 'error',
52
+ 'brace-style': ['error', '1tbs', { allowSingleLine: true }],
53
+ camelcase: ['error', { properties: 'never' }],
54
+ 'comma-spacing': ['error', { before: false, after: true }],
55
+ 'eol-last': ['error', 'always'],
56
+ 'key-spacing': ['error', { beforeColon: false, afterColon: true, mode: 'minimum' }],
57
+ 'keyword-spacing': ['error', {}],
58
+ 'no-cond-assign': 'error',
59
+ 'no-console': ['off', { allow: ['warn', 'error'] }],
60
+ 'no-constant-condition': ['error', { checkLoops: false }],
61
+ 'no-eval': 'error',
62
+ 'no-fallthrough': 'off',
63
+ 'no-mixed-spaces-and-tabs': 'error',
64
+ 'no-restricted-globals': ['error', 'event'],
65
+ 'no-restricted-syntax': [
66
+ 'error',
67
+ {
68
+ selector:
69
+ "*:not(ExpressionStatement) > CallExpression[callee.property.name='sort']:not([callee.object.type='CallExpression']):not([callee.object.type='ArrayExpression']):not([callee.object.name='mongoUtil'])",
70
+ message:
71
+ 'Restricted Array Mutation: Use `array.slice().sort(...)` if mutation was not intended, otherwise place on own line.',
72
+ },
73
+ {
74
+ selector:
75
+ "*:not(ExpressionStatement) > CallExpression[callee.property.name='reverse']:not([callee.object.type='CallExpression']):not([callee.object.type='ArrayExpression'])",
76
+ message:
77
+ 'Restricted Array Mutation: Use `array.slice().reverse(...)` if mutation was not intended, otherwise place on own line.',
78
+ },
79
+ {
80
+ selector: "*:not(ExpressionStatement) > CallExpression[callee.property.name='push']",
81
+ message:
82
+ 'Restricted Array Mutation: `array.push(...)` returns push count, not array reference, place statement on own line.',
83
+ },
84
+ ],
85
+ 'no-undef': 'error',
86
+ 'no-unused-expressions': 'error',
87
+ 'no-unused-vars': ['error', { vars: 'all', args: 'none' }],
88
+ 'no-useless-escape': 'off',
89
+ 'no-with': 'error',
90
+ 'padding-line-between-statements': ['error', { blankLine: 'always', prev: '*', next: 'function' }],
91
+ semi: ['error', 'always'],
92
+ 'space-before-blocks': ['error', 'always'],
93
+ },
94
+ },
95
+ ];
@@ -31,8 +31,8 @@ if (options.s) {
31
31
  mib.setScalarValue(providerName, change);
32
32
  }
33
33
  }
34
- } catch (e) {
35
- console.log("Could not parse persistent storage");
34
+ } catch (error) {
35
+ console.log("Could not parse persistent storage", error);
36
36
  changes = {};
37
37
  }
38
38
  }
package/index.js CHANGED
@@ -2882,9 +2882,17 @@ Listener.processIncoming = function (buffer, authorizer, callback) {
2882
2882
  return message;
2883
2883
  };
2884
2884
 
2885
- Listener.prototype.close = function () {
2885
+ Listener.prototype.close = function (callback) {
2886
2886
  for ( const socket of Object.values(this.sockets) ) {
2887
- socket.close ();
2887
+ if ( callback ) {
2888
+ const socketInfo = socket.address();
2889
+ const socketCallback = () => {
2890
+ callback(socketInfo);
2891
+ };
2892
+ socket.close (socketCallback);
2893
+ } else {
2894
+ socket.close();
2895
+ }
2888
2896
  }
2889
2897
  };
2890
2898
 
@@ -3168,8 +3176,8 @@ Receiver.prototype.formatCallbackData = function (message, rinfo) {
3168
3176
  return formattedData;
3169
3177
  };
3170
3178
 
3171
- Receiver.prototype.close = function() {
3172
- this.listener.close ();
3179
+ Receiver.prototype.close = function (callback) {
3180
+ this.listener.close (callback);
3173
3181
  };
3174
3182
 
3175
3183
  Receiver.create = function (options, callback) {
@@ -3764,6 +3772,7 @@ MibNode.prototype.getNextInstanceNode = function () {
3764
3772
  // end of MIB
3765
3773
  return null;
3766
3774
  } else {
3775
+ // Move to next sibling
3767
3776
  childrenAddresses = Object.keys (node.children).sort ( (a, b) => a - b);
3768
3777
  var siblingPosition = childrenAddresses.indexOf(siblingIndex.toString());
3769
3778
  if ( siblingPosition + 1 < childrenAddresses.length ) {
@@ -3773,11 +3782,11 @@ MibNode.prototype.getNextInstanceNode = function () {
3773
3782
  }
3774
3783
  }
3775
3784
  }
3776
- // Descent
3777
3785
  while ( node ) {
3778
3786
  if ( node.value != null ) {
3779
3787
  return node;
3780
3788
  }
3789
+ // Descend to first child if not at leaf
3781
3790
  childrenAddresses = Object.keys (node.children).sort ( (a, b) => a - b);
3782
3791
  node = node.children[childrenAddresses[0]];
3783
3792
  if ( ! node ) {
@@ -5257,6 +5266,7 @@ Agent.prototype.addGetNextVarbind = function (targetVarbinds, startOid) {
5257
5266
 
5258
5267
  try {
5259
5268
  startNode = this.mib.lookup (startOid);
5269
+ // eslint-disable-next-line no-unused-vars
5260
5270
  } catch ( error ) {
5261
5271
  startOid = '1.3.6.1';
5262
5272
  startNode = this.mib.lookup (startOid);
@@ -5392,8 +5402,8 @@ Agent.prototype.getForwarder = function () {
5392
5402
  return this.forwarder;
5393
5403
  };
5394
5404
 
5395
- Agent.prototype.close = function() {
5396
- this.listener.close ();
5405
+ Agent.prototype.close = function (callback) {
5406
+ this.listener.close (callback);
5397
5407
  };
5398
5408
 
5399
5409
  Agent.create = function (options, callback, mib) {
@@ -6199,6 +6209,7 @@ Subagent.prototype.addGetNextVarbind = function (targetVarbinds, startOid) {
6199
6209
 
6200
6210
  try {
6201
6211
  startNode = this.mib.lookup (startOid);
6212
+ // eslint-disable-next-line no-unused-vars
6202
6213
  } catch ( error ) {
6203
6214
  startOid = '1.3.6.1';
6204
6215
  startNode = this.mib.lookup (startOid);
package/lib/mib.js CHANGED
@@ -346,6 +346,7 @@ var MIB = function (dir) {
346
346
  var Symbols = this.SymbolBuffer[ModuleName];
347
347
  var Object = Module;
348
348
  var MACROName = '';
349
+ let unresolvedObjects = [];
349
350
  for (var i = 0; i < Symbols.length; i++) {
350
351
  switch (Symbols[i]) {
351
352
  case '::=': //new OBJECT to define
@@ -372,9 +373,14 @@ var MIB = function (dir) {
372
373
  Object[Symbols[i - 2]]['OID'] = '0.0';
373
374
  Object[Symbols[i - 2]]['NameSpace'] = 'null';
374
375
  } else {
375
- const { oidString, nameString } = this.getOidAndNamePaths(Object[Symbols[i - 2]]['OBJECT IDENTIFIER'], Symbols[i - 2], ModuleName);
376
+ const { oidString, nameString, unresolvedObject } = this.getOidAndNamePaths(Object[Symbols[i - 2]]['OBJECT IDENTIFIER'], Symbols[i - 2], ModuleName);
376
377
  Object[Symbols[i - 2]]['OID'] = oidString;
377
378
  Object[Symbols[i - 2]]['NameSpace'] = nameString;
379
+ if (unresolvedObject) {
380
+ if ( ! unresolvedObjects.includes(unresolvedObject) ) {
381
+ unresolvedObjects.push(unresolvedObject);
382
+ }
383
+ }
378
384
  // Object[Symbols[i - 2]]['ModuleName'] = ModuleName;
379
385
  // Object[Symbols[i - 2]]['ObjectName'] = Symbols[i - 2];
380
386
  }
@@ -531,11 +537,14 @@ var MIB = function (dir) {
531
537
  Object[Symbols[r - 1]]['OID'] = '0.0';
532
538
  Object[Symbols[r - 1]]['NameSpace'] = 'null';
533
539
  } else {
534
- const { oidString, nameString } = this.getOidAndNamePaths(Object[Symbols[r - 1]]['OBJECT IDENTIFIER'], Symbols[r - 1], ModuleName);
540
+ const { oidString, nameString, unresolvedObject } = this.getOidAndNamePaths(Object[Symbols[r - 1]]['OBJECT IDENTIFIER'], Symbols[r - 1], ModuleName);
535
541
  Object[Symbols[r - 1]]['OID'] = oidString;
536
542
  Object[Symbols[r - 1]]['NameSpace'] = nameString;
537
- // Object[Symbols[r - 1]]['ModuleName'] = ModuleName;
538
- // Object[Symbols[r - 1]]['ObjectName'] = Symbols[r - 1];
543
+ if (unresolvedObject) {
544
+ if ( ! unresolvedObjects.includes(unresolvedObject) ) {
545
+ unresolvedObjects.push(unresolvedObject);
546
+ }
547
+ }
539
548
  }
540
549
  if ( Object[Symbols[r - 1]]['REVISIONS-DESCRIPTIONS'] &&
541
550
  Object[Symbols[r - 1]]['REVISIONS-DESCRIPTIONS'].length == 1 &&
@@ -643,6 +652,29 @@ var MIB = function (dir) {
643
652
 
644
653
 
645
654
  }
655
+ // attempt OID/namespace reconstruction for unresolved objects, as parsing has finished
656
+ if (unresolvedObjects.length > 0) {
657
+ for (const unresolved of unresolvedObjects) {
658
+ const obj = this.Modules[ModuleName][unresolved];
659
+
660
+ const { oidString, nameString, unresolvedObject } = this.getOidAndNamePaths(obj['OBJECT IDENTIFIER'], unresolved, ModuleName);
661
+ this.Modules[ModuleName][unresolved].NameSpace = nameString;
662
+ this.Modules[ModuleName][unresolved].OID = oidString;
663
+
664
+ // unresolvedObject is only returned if still unable to resolve (likely due to error in MIB)
665
+ // unresolved OID will propagate to all children as well
666
+ if (unresolvedObject) {
667
+ if (obj.NameSpace) {
668
+ const unresolvedParent = obj.NameSpace.split('.')[1];
669
+ if (unresolvedParent !== obj.ObjectName) {
670
+ console.warn(`Unable to mount node '${obj.ObjectName}', cannot resolve parent object '${unresolvedParent}'.`);
671
+ continue;
672
+ }
673
+ }
674
+ console.warn(`Unable to mount node '${obj.ObjectName}', cannot resolve object identifier '${obj['OBJECT IDENTIFIER']}'.`);
675
+ }
676
+ }
677
+ }
646
678
  }
647
679
  }
648
680
  },
@@ -761,6 +793,7 @@ var MIB = function (dir) {
761
793
  nameEntries.push(ObjectName);
762
794
  let parentOidPrefix;
763
795
  let parentNamePrefix;
796
+ let unresolvedObject;
764
797
  if ( parent == 'iso' ) {
765
798
  parentOidPrefix = '1';
766
799
  parentNamePrefix = 'iso';
@@ -780,18 +813,25 @@ var MIB = function (dir) {
780
813
  }
781
814
  if ( ! parentObject ) {
782
815
  // occurs for out-of-order dependencies in a module
783
- // console.warn('Parent object not found for ' + parent);
816
+ // return partial OID/namespace and name of unresolved object
817
+ unresolvedObject = ObjectName;
784
818
  return {
785
- oidString: '',
786
- nameString: ''
819
+ oidString: '.' + oidEntries.join('.'),
820
+ nameString: '.' + nameEntries.join('.'),
821
+ unresolvedObject
787
822
  };
788
823
  }
824
+ // occurs for all children of an unresolved node
825
+ if ( parentObject.OID.startsWith('.') ) {
826
+ unresolvedObject = ObjectName;
827
+ }
789
828
  parentOidPrefix = parentObject['OID'];
790
829
  parentNamePrefix = parentObject['NameSpace'];
791
830
  }
792
831
  return {
793
832
  oidString: parentOidPrefix + '.' + oidEntries.join('.'),
794
- nameString: parentNamePrefix + '.' + nameEntries.join('.')
833
+ nameString: parentNamePrefix + '.' + nameEntries.join('.'),
834
+ unresolvedObject: unresolvedObject || undefined
795
835
  };
796
836
  }
797
837
  });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "net-snmp",
3
- "version": "3.12.1",
3
+ "version": "3.13.1",
4
4
  "description": "JavaScript implementation of the Simple Network Management Protocol (SNMP)",
5
5
  "main": "index.js",
6
6
  "directories": {
@@ -11,7 +11,7 @@
11
11
  "smart-buffer": "^4.1.0"
12
12
  },
13
13
  "devDependencies": {
14
- "eslint": "^5.16.0",
14
+ "eslint": "^9.9.1",
15
15
  "getopts": "*"
16
16
  },
17
17
  "contributors": [
package/.eslintrc DELETED
@@ -1,76 +0,0 @@
1
- {
2
- "extends": "eslint:recommended",
3
- "env": {
4
- "es6": true,
5
- "node": true,
6
- "browser": true,
7
- "mocha": true
8
- },
9
- "parserOptions": {
10
- "ecmaVersion": 2016
11
- },
12
- "globals": {
13
- "window": false,
14
- "document": false,
15
- "$": false,
16
- "System": false,
17
- "expect": false
18
- },
19
- "rules": {
20
- "accessor-pairs": "error",
21
- "arrow-spacing": "error",
22
- "brace-style": [ "error", "1tbs", { "allowSingleLine": true } ],
23
- "camelcase": [ "error", { "properties": "never" } ],
24
- "comma-spacing": ["error", { "before": false, "after": true }],
25
- // "curly": [ "error", "all" ],
26
- // "dot-notation": "error",
27
- "eol-last": ["error", "always"],
28
- // "eqeqeq": ["error", "always"],
29
- // "indent": ["error", "tab", { "MemberExpression": "off", "SwitchCase": 1, "ObjectExpression": "first" } ],
30
- "key-spacing": [ "error", { "beforeColon": false, "afterColon": true, "mode": "minimum" } ],
31
- "keyword-spacing": [ "error", {} ],
32
- "no-cond-assign": "error",
33
- "no-console": ["off", { "allow": ["warn", "error"] }],
34
- "no-constant-condition": ["error", { "checkLoops": false }],
35
- "no-eval": "error",
36
- "no-fallthrough": "off",
37
- "no-mixed-spaces-and-tabs": "error",
38
- // "no-multiple-empty-lines": "error",
39
- "no-restricted-globals": ["error", "event"],
40
- "no-restricted-syntax": [
41
- "error",
42
- {
43
- "selector": "*:not(ExpressionStatement) > CallExpression[callee.property.name='sort']:not([callee.object.type='CallExpression']):not([callee.object.type='ArrayExpression']):not([callee.object.name='mongoUtil'])",
44
- "message": "Restricted Array Mutation: Use `array.slice().sort(...)` if mutation was not intended, otherwise place on own line."
45
- },
46
- {
47
- "selector": "*:not(ExpressionStatement) > CallExpression[callee.property.name='reverse']:not([callee.object.type='CallExpression']):not([callee.object.type='ArrayExpression'])",
48
- "message": "Restricted Array Mutation: Use `array.slice().reverse(...)` if mutation was not intended, otherwise place on own line."
49
- },
50
- {
51
- "selector": "*:not(ExpressionStatement) > CallExpression[callee.property.name='push']",
52
- "message": "Restricted Array Mutation: `array.push(...)` returns push count, not array reference, place statement on own line."
53
- }
54
- ],
55
- // "no-return-assign": "error",
56
- // "no-trailing-spaces": "error",
57
- "no-undef": "error",
58
- "no-unused-expressions": "error",
59
- "no-unused-vars": ["error", { "vars": "all", "args": "none" }],
60
- // "no-use-before-define": [ "error", { "functions": false } ],
61
- "no-useless-escape": "off",
62
- "no-with": "error",
63
- "padding-line-between-statements": [
64
- "error",
65
- { "blankLine": "always", "prev": "*", "next": "function" }
66
- ],
67
- // "quotes": [ "error", "double", { "allowTemplateLiterals": true, "avoidEscape": true } ],
68
- "semi": [ "error", "always" ],
69
- "space-before-blocks": [ "error", "always" ],
70
- // "space-before-function-paren": [ "error", { "anonymous": "always", "named": "always", "asyncArrow": "always" } ],
71
- // "space-in-parens": [ "error", "never" ],
72
- // "space-infix-ops": "error",
73
- // "space-unary-ops": [ "error", { "nonwords": true, "overrides": {} } ],
74
- // "spaced-comment": [ "error", "always", {"block": {"exceptions": ["*", "!"], "balanced": true}} ]
75
- }
76
- }