camstreamerlib 3.2.0 → 3.2.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.
@@ -1,3 +1,4 @@
1
1
  export declare class Digest {
2
- static getAuthHeader(user: string, pass: string, method: string, uri: string, wwwAuthenticateHeader: string): string;
2
+ private nonceCount;
3
+ getAuthHeader(user: string, pass: string, method: string, uri: string, wwwAuthenticateHeader: string): string;
3
4
  }
@@ -3,7 +3,10 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.Digest = void 0;
4
4
  const crypto = require("crypto");
5
5
  class Digest {
6
- static getAuthHeader(user, pass, method, uri, wwwAuthenticateHeader) {
6
+ constructor() {
7
+ this.nonceCount = 1;
8
+ }
9
+ getAuthHeader(user, pass, method, uri, wwwAuthenticateHeader) {
7
10
  const digestItems = {};
8
11
  const digestArr = wwwAuthenticateHeader.substring(wwwAuthenticateHeader.indexOf('Digest') + 6).split(',');
9
12
  for (let i = 0; i < digestArr.length; i++) {
@@ -14,11 +17,12 @@ class Digest {
14
17
  }
15
18
  const HA1 = crypto.createHash('md5').update(`${user}:${digestItems['realm']}:${pass}`).digest('hex');
16
19
  const HA2 = crypto.createHash('md5').update(`${method}:${uri}`).digest('hex');
20
+ const ncValue = ('00000000' + this.nonceCount.toString(16)).slice(-8);
17
21
  let response;
18
22
  if (digestItems['qop'] !== undefined) {
19
23
  response = crypto
20
24
  .createHash('md5')
21
- .update(`${HA1}:${digestItems['nonce']}:00000001:162d50aa594e9648:auth:${HA2}`)
25
+ .update(`${HA1}:${digestItems['nonce']}:${ncValue}:162d50aa594e9648:auth:${HA2}`)
22
26
  .digest('hex');
23
27
  }
24
28
  else {
@@ -31,8 +35,9 @@ class Digest {
31
35
  `uri="${uri}",` +
32
36
  `response="${response}"`;
33
37
  if (digestItems['qop'] !== undefined) {
34
- header += ',qop=auth,nc=00000001,cnonce="162d50aa594e9648"';
38
+ header += `,qop=auth,nc=${ncValue},cnonce="162d50aa594e9648"`;
35
39
  }
40
+ this.nonceCount++;
36
41
  return header;
37
42
  }
38
43
  }
@@ -24,5 +24,5 @@ export declare class HttpRequestSender {
24
24
  private static getURL;
25
25
  private getAuthorization;
26
26
  private invalidateAuthorization;
27
- private getAuthHeader;
27
+ private static getAuthHeader;
28
28
  }
@@ -37,10 +37,10 @@ class HttpRequestSender {
37
37
  if (options.timeout !== undefined) {
38
38
  setTimeout(() => controller.abort(new Error('Request timeout')), options.timeout);
39
39
  }
40
- const authData = this.getAuthorization(options, wwwAuthenticateHeader);
41
- if (authData) {
40
+ const authorization = this.getAuthorization(options, wwwAuthenticateHeader);
41
+ if (authorization !== undefined) {
42
42
  (_a = options.headers) !== null && _a !== void 0 ? _a : (options.headers = {});
43
- options.headers['Authorization'] = authData.authHeader;
43
+ options.headers['Authorization'] = authorization;
44
44
  }
45
45
  let res;
46
46
  if (this.agent) {
@@ -51,8 +51,10 @@ class HttpRequestSender {
51
51
  const req = new Request(url, { body: postData, method: options.method, headers: options.headers });
52
52
  res = yield fetch(req, { signal: controller.signal });
53
53
  }
54
- if (res.status === 401) {
54
+ if (!res.ok) {
55
55
  this.invalidateAuthorization();
56
+ }
57
+ if (res.status === 401) {
56
58
  const authenticateHeader = res.headers.get('www-authenticate');
57
59
  if (authenticateHeader !== null &&
58
60
  authenticateHeader.indexOf('Digest') !== -1 &&
@@ -81,7 +83,8 @@ class HttpRequestSender {
81
83
  (this.authData.host !== options.host ||
82
84
  this.authData.port !== options.port ||
83
85
  this.authData.user !== options.user ||
84
- this.authData.pass !== options.pass)) {
86
+ this.authData.pass !== options.pass ||
87
+ (wwwAuthenticateHeader !== undefined && this.authData.wwwAuthenticateHeader !== wwwAuthenticateHeader))) {
85
88
  this.authData = undefined;
86
89
  }
87
90
  if (this.authData === undefined) {
@@ -90,21 +93,22 @@ class HttpRequestSender {
90
93
  port: options.port,
91
94
  user: options.user,
92
95
  pass: options.pass,
93
- authHeader: this.getAuthHeader(options, wwwAuthenticateHeader),
96
+ wwwAuthenticateHeader,
97
+ digest: new Digest_1.Digest(),
94
98
  };
95
99
  }
96
- return this.authData;
100
+ return HttpRequestSender.getAuthHeader(options, this.authData);
97
101
  }
98
102
  invalidateAuthorization() {
99
103
  this.authData = undefined;
100
104
  }
101
- getAuthHeader(options, wwwAuthenticateHeader = '') {
105
+ static getAuthHeader(options, authData) {
102
106
  var _a;
103
107
  if (options.user === undefined || options.pass === undefined) {
104
108
  throw new Error('No credentials found');
105
109
  }
106
- if (wwwAuthenticateHeader.indexOf('Digest') !== -1) {
107
- return Digest_1.Digest.getAuthHeader(options.user, options.pass, (_a = options.method) !== null && _a !== void 0 ? _a : 'GET', options.path, wwwAuthenticateHeader);
110
+ if (authData.wwwAuthenticateHeader !== undefined && authData.wwwAuthenticateHeader.indexOf('Digest') !== -1) {
111
+ return authData.digest.getAuthHeader(options.user, options.pass, (_a = options.method) !== null && _a !== void 0 ? _a : 'GET', options.path, authData.wwwAuthenticateHeader);
108
112
  }
109
113
  else {
110
114
  return `Basic ${btoa(options.user + ':' + options.pass)}`;
@@ -65,7 +65,7 @@ class WsClient extends EventEmitter {
65
65
  this.isAlive = true;
66
66
  });
67
67
  if (wwwAuthenticateHeader !== undefined) {
68
- this.wsOptions.headers['Authorization'] = Digest_1.Digest.getAuthHeader(this.user, this.pass, 'GET', this.digestAddress, wwwAuthenticateHeader);
68
+ this.wsOptions.headers['Authorization'] = new Digest_1.Digest().getAuthHeader(this.user, this.pass, 'GET', this.digestAddress, wwwAuthenticateHeader);
69
69
  }
70
70
  this.ws.on('unexpected-response', (req, res) => __awaiter(this, void 0, void 0, function* () {
71
71
  var _b;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "camstreamerlib",
3
- "version": "3.2.0",
3
+ "version": "3.2.1",
4
4
  "description": "Helper library for CamStreamer ACAP applications.",
5
5
  "prettier": "@camstreamer/prettier-config",
6
6
  "dependencies": {