@adobe/acc-js-sdk 1.0.2 → 1.0.6

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,4 +1,3 @@
1
- "use strict";
2
1
  /*
3
2
  Copyright 2020 Adobe. All rights reserved.
4
3
  This file is licensed to you under the Apache License, Version 2.0 (the "License");
@@ -10,7 +9,8 @@ the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR REPRESENTA
10
9
  OF ANY KIND, either express or implied. See the License for the specific language
11
10
  governing permissions and limitations under the License.
12
11
  */
13
-
12
+ (function() {
13
+ "use strict";
14
14
 
15
15
  /**********************************************************************************
16
16
  *
@@ -18,6 +18,8 @@ governing permissions and limitations under the License.
18
18
  *
19
19
  *********************************************************************************/
20
20
  const XtkCaster = require('./xtkCaster.js').XtkCaster;
21
+ const { Cache } = require('./cache.js');
22
+
21
23
 
22
24
  /**
23
25
  * @namespace Campaign
@@ -31,23 +33,40 @@ const XtkCaster = require('./xtkCaster.js').XtkCaster;
31
33
 
32
34
 
33
35
  /**
34
- * A in-memory cache for xtk option values. Not intended to be used directly,
35
- * but an internal cache for the Campaign.Client object
36
- *
37
36
  * @private
38
37
  * @class
39
38
  * @constructor
40
39
  * @memberof Campaign
41
40
  */
42
- class OptionCache {
41
+ class OptionCache extends Cache {
43
42
 
44
- constructor() {
45
- /**
46
- * The option values, by option name
47
- * @private
48
- * @type {Object<string,Campaign.XtkOption>}
49
- */
50
- this._optionsByName = {};
43
+ /**
44
+ * A in-memory cache for xtk option values. Not intended to be used directly,
45
+ * but an internal cache for the Campaign.Client object
46
+ *
47
+ * Cached object are made of
48
+ * - the key is the option name
49
+ * - the value is the option, a JSON object made of value, type, and rawValue properties
50
+ *
51
+ * @param {Storage} storage is an optional Storage object, such as localStorage or sessionStorage
52
+ * @param {string} rootKey is an optional root key to use for the storage object
53
+ * @param {number} ttl is the TTL for objects in ms. Defaults to 5 mins
54
+ */
55
+ constructor(storage, rootKey, ttl) {
56
+ super(storage, rootKey, ttl);
57
+ }
58
+
59
+ /**
60
+ * Cache an option and its value
61
+ * For backward compatibility purpose. Use "put" instead
62
+ *
63
+ * @deprecated
64
+ * @param {string} name is the option name
65
+ * @param {Array} rawValueAndtype a 2 elements array, whose first element is the raw option value (text serialized) and the second element
66
+ * is the data type of the option. Such an array is returned by the xtk:session#GetOption method
67
+ */
68
+ cache(schemaId, methodName) {
69
+ return this.put(schemaId, methodName);
51
70
  }
52
71
 
53
72
  /**
@@ -57,16 +76,16 @@ class OptionCache {
57
76
  * @param {Array} rawValueAndtype a 2 elements array, whose first element is the raw option value (text serialized) and the second element
58
77
  * is the data type of the option. Such an array is returned by the xtk:session#GetOption method
59
78
  */
60
- cache(name, rawValueAndtype) {
79
+ put(name, rawValueAndtype) {
61
80
  var value = null;
62
81
  var type = 0;
63
- var rawValue = undefined;
82
+ var rawValue;
64
83
  if (rawValueAndtype && rawValueAndtype[1] != 0) {
65
84
  rawValue = rawValueAndtype[0];
66
85
  type = rawValueAndtype[1];
67
86
  value = XtkCaster.as(rawValue, type);
68
87
  }
69
- this._optionsByName[name] = { value:value, type:type, rawValue:rawValue };
88
+ super.put(name, { value:value, type:type, rawValue:rawValue });
70
89
  return value;
71
90
  }
72
91
 
@@ -77,7 +96,7 @@ class OptionCache {
77
96
  * @returns {*} the option value
78
97
  */
79
98
  get(name) {
80
- const option = this._optionsByName[name];
99
+ const option = super.get(name);
81
100
  return option ? option.value : undefined;
82
101
  }
83
102
 
@@ -88,19 +107,12 @@ class OptionCache {
88
107
  * @returns {Campaign.XtkOption} the option
89
108
  */
90
109
  getOption(name) {
91
- const option = this._optionsByName[name];
92
- return option;
110
+ return super.get(name);
93
111
  }
94
-
95
- /**
96
- * Clears the cache
97
- */
98
- clear() {
99
- this._optionsByName = {};
100
- }
101
-
102
112
  }
103
113
 
104
114
 
105
115
  // Public exports
106
- exports.OptionCache = OptionCache;
116
+ exports.OptionCache = OptionCache;
117
+
118
+ })();
package/src/soap.js CHANGED
@@ -1,4 +1,3 @@
1
- "use strict";
2
1
  /*
3
2
  Copyright 2020 Adobe. All rights reserved.
4
3
  This file is licensed to you under the Apache License, Version 2.0 (the "License");
@@ -10,7 +9,9 @@ the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR REPRESENTA
10
9
  OF ANY KIND, either express or implied. See the License for the specific language
11
10
  governing permissions and limitations under the License.
12
11
  */
13
-
12
+ (function() {
13
+ "use strict";
14
+
14
15
 
15
16
  /**********************************************************************************
16
17
  *
@@ -118,7 +119,8 @@ class SoapMethodCall {
118
119
  * @returns {boolean} indicates if the call requires a Logon first
119
120
  */
120
121
  requiresLogon() {
121
- const requiresLogon = !(this.urn === "xtk:session" && this.methodName === "Logon");
122
+ const requiresLogon = !(this.urn === "xtk:session" &&
123
+ (this.methodName === "Logon" || this.methodName === "BearerTokenLogon") ) ;
122
124
  return requiresLogon;
123
125
  }
124
126
 
@@ -150,14 +152,20 @@ class SoapMethodCall {
150
152
  this._method.setAttribute(`SOAP-ENV:encodingStyle`, encoding);
151
153
  this._data.appendChild(this._method);
152
154
 
153
- const cookieHeader = this._doc.createElement("Cookie");
154
- cookieHeader.textContent = `__sessiontoken=${this._sessionToken}`;
155
- this._header.appendChild(cookieHeader);
155
+ if (this._sessionToken) {
156
+ const cookieHeader = this._doc.createElement("Cookie");
157
+ cookieHeader.textContent = `__sessiontoken=${this._sessionToken}`;
158
+ this._header.appendChild(cookieHeader);
159
+ }
156
160
 
157
161
  const securityTokenHeader = this._doc.createElement("X-Security-Token");
158
162
  securityTokenHeader.textContent = this._securityToken;
159
163
  this._header.appendChild(securityTokenHeader);
160
164
 
165
+ // Always write a sessiontoken element as the first parameter. Even when using SecurityToken authentication
166
+ // and when the session token is actually passed implicitely as a cookie, one must write a sessiontoken
167
+ // element. If not, authentication will fail because the first parameter is interpreted as the "authentication mode"
168
+ // and eventually passed as the first parameter of CXtkLocalSessionPart::GetXtkSecurity
161
169
  this.writeString("sessiontoken", this._sessionToken);
162
170
  }
163
171
 
@@ -508,7 +516,7 @@ class SoapMethodCall {
508
516
  * @returns a boolean set to true if ther are no more response args to read
509
517
  */
510
518
  checkNoMoreArgs() {
511
- return !this.elemCurrent
519
+ return !this.elemCurrent;
512
520
  }
513
521
 
514
522
  /**
@@ -524,11 +532,12 @@ class SoapMethodCall {
524
532
  headers: {
525
533
  'Content-type': 'application/soap+xml',
526
534
  'SoapAction': `${this.urn}#${this.methodName}`,
527
- 'X-Security-Token': this._securityToken,
528
- 'Cookie': '__sessiontoken=' + this._sessionToken
535
+ 'X-Security-Token': this._securityToken
529
536
  },
530
537
  data: DomUtil.toXMLString(this._doc)
531
538
  };
539
+ if (this._sessionToken)
540
+ options.headers.Cookie = '__sessiontoken=' + this._sessionToken;
532
541
  if (this._userAgentString)
533
542
  options.headers['User-Agent'] = this._userAgentString;
534
543
  return options;
@@ -629,3 +638,5 @@ class SoapMethodCall {
629
638
 
630
639
  // Public exports
631
640
  exports.SoapMethodCall = SoapMethodCall;
641
+
642
+ })();
package/src/transport.js CHANGED
@@ -9,6 +9,8 @@ the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR REPRESENTA
9
9
  OF ANY KIND, either express or implied. See the License for the specific language
10
10
  governing permissions and limitations under the License.
11
11
  */
12
+ (function() {
13
+ "use strict";
12
14
 
13
15
  const { Util } = require('./util.js');
14
16
 
@@ -52,7 +54,7 @@ if (!Util.isBrowser()) {
52
54
 
53
55
  const request = (options) => {
54
56
  const request = {
55
- method: options.method,
57
+ method: options.method || "GET",
56
58
  url: options.url,
57
59
  headers: options.headers,
58
60
  data: options.data,
@@ -70,9 +72,8 @@ if (!Util.isBrowser()) {
70
72
  return Promise.reject(new HttpError(500, error ? error.toString() : undefined));
71
73
  // HTTP errors (400, 404, 500, etc.) are returned here
72
74
  return Promise.reject(new HttpError(response.status, response.statusText, response.data));
73
- })
74
- }
75
-
75
+ });
76
+ };
76
77
 
77
78
  exports.request = request;
78
79
  exports.HttpError = HttpError;
@@ -107,13 +108,16 @@ if (!Util.isBrowser()) {
107
108
  return blob.text();
108
109
  });
109
110
  }).catch((ex) => {
110
- if (ex.__proto__.constructor.name == "HttpError")
111
+ const proto = Object.getPrototypeOf(ex);
112
+ if (proto.constructor.name == "HttpError")
111
113
  throw ex;
112
114
  throw new HttpError(ex.status, ex.statusText);
113
- })
115
+ });
114
116
  return p;
115
- }
117
+ };
116
118
 
117
119
  module.exports.request = request;
118
120
 
119
- }
121
+ }
122
+
123
+ })();
package/src/util.js CHANGED
@@ -1,5 +1,3 @@
1
- "use strict";
2
-
3
1
  /*
4
2
  Copyright 2020 Adobe. All rights reserved.
5
3
  This file is licensed to you under the Apache License, Version 2.0 (the "License");
@@ -11,7 +9,9 @@ the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR REPRESENTA
11
9
  OF ANY KIND, either express or implied. See the License for the specific language
12
10
  governing permissions and limitations under the License.
13
11
  */
14
-
12
+ (function() {
13
+ "use strict";
14
+
15
15
 
16
16
  /**********************************************************************************
17
17
  *
@@ -20,83 +20,122 @@ governing permissions and limitations under the License.
20
20
  *********************************************************************************/
21
21
 
22
22
  /**
23
- * @namespace Campaign
23
+ * @namespace Utils
24
24
  */
25
25
 
26
26
  /**
27
- * Helpers for common manipulation of DOM documents
28
- * @memberof Campaign
27
+ * @memberof Utils
29
28
  * @class
30
29
  * @constructor
31
30
  */
32
31
  class Util {
33
32
 
34
- static isBrowser() {
35
- const browser = typeof window !== 'undefined';
36
- return browser;
37
- }
38
-
39
- static isArray(o) {
40
- if (o === null || o === undefined) return false;
41
- // JavaScript arrays are objects
42
- if (typeof o != "object") return false;
43
- // They also have a length property. But checking the length is not enough
44
- // since, it can also be an object litteral with a "length" property. Campaign
45
- // schema attributes typically have a "length" attribute and are not arrays
46
- if (o.length === undefined || o.length === null) return false;
47
- // So check for a "push" function
48
- if (o.push === undefined || o.push === null) return false;
49
- if (typeof o.push != "function")
50
- return false;
51
- return true;
52
- }
33
+ /**
34
+ * Generic helper functions available everywhere in the SDK. Al functions are static, it is not necessary to create new instances of this object
35
+ */
36
+ constructor() {
37
+ }
53
38
 
39
+ /**
40
+ * Indicates whether the SDK is running in a browser or not
41
+ * @returns {boolean} a boolean indicating if the SDK is running in a browser or not
42
+ */
43
+ static isBrowser() {
44
+ const browser = typeof window !== 'undefined';
45
+ return browser;
46
+ }
47
+
48
+ /**
49
+ * Tests if an object is a JavaScript array
50
+ * @param {*} obj the object to test, may be undefined
51
+ * @returns {boolean} true if the object is an array
52
+ */
53
+ static isArray(obj) {
54
+ if (obj === null || obj === undefined) return false;
55
+ // JavaScript arrays are objects
56
+ if (typeof obj != "object") return false;
57
+ // They also have a length property. But checking the length is not enough
58
+ // since, it can also be an object litteral with a "length" property. Campaign
59
+ // schema attributes typically have a "length" attribute and are not arrays
60
+ if (obj.length === undefined || obj.length === null) return false;
61
+ // So check for a "push" function
62
+ if (obj.push === undefined || obj.push === null) return false;
63
+ if (typeof obj.push != "function")
64
+ return false;
65
+ return true;
66
+ }
54
67
 
55
- static _removeBetween(text, from, to) {
56
- var index = 0;
57
- while (index < text.length) {
58
- index = text.indexOf(from, index);
59
- if (index == -1) break;
60
- const index2 = text.indexOf(to, index);
61
- if (index2 == -1) {
62
- break;
63
- }
64
- text = text.substring(0, index + from.length) + '***' + text.substring(index2);
65
- index = index2;
66
- }
67
- return text;
68
+ // Helper function for trim() to replace text between 2 indices
69
+ static _removeBetween(text, from, to) {
70
+ var index = 0;
71
+ while (index < text.length) {
72
+ index = text.indexOf(from, index);
73
+ if (index == -1) break;
74
+ const index2 = text.indexOf(to, index);
75
+ if (index2 == -1) {
76
+ break;
68
77
  }
69
-
70
- static trim(text) {
71
- if (text == null || text == undefined) return undefined;
72
- if (Util.isArray(text)) {
73
- const a = [];
74
- for (const p of text) {
75
- a.push(Util.trim(p));
76
- }
77
- return a;
78
- }
79
- if (typeof text == "object") {
80
- for (const p in text) {
81
- text[p] = Util.trim(text[p]);
78
+ text = text.substring(0, index + from.length) + '***' + text.substring(index2);
79
+ index = index2;
80
+ }
81
+ return text;
82
+ }
83
+
84
+ /**
85
+ * Trims a text, an object or an array and remove sensitive information, such as session tokens, passwords, etc.
86
+ *
87
+ * @param {string|Object|Array} obj is the object to trim
88
+ * @returns {string|Object|Array} the trimmed object
89
+ */
90
+ static trim(obj) {
91
+ if (obj == null || obj == undefined) return undefined;
92
+ if (Util.isArray(obj)) {
93
+ const a = [];
94
+ for (const p of obj) {
95
+ a.push(Util.trim(p));
96
+ }
97
+ return a;
98
+ }
99
+ if (typeof obj == "object") {
100
+ for (const p in obj) {
101
+ if (p.toLowerCase() === "x-security-token")
102
+ obj[p] = "***";
103
+ else if (p === "Cookie") {
104
+ var index = obj[p].toLowerCase().indexOf("__sessiontoken");
105
+ if (index !== -1) {
106
+ index = obj[p].indexOf("=", index);
107
+ if (index !== -1) {
108
+ index = index + 1;
109
+ const endIndex = obj[p].indexOf(";", index);
110
+ if (endIndex == -1)
111
+ obj[p] = obj[p].substring(0, index) + "***";
112
+ else
113
+ obj[p] = obj[p].substring(0, index) + "***" + obj[p].substring(endIndex);
114
+ }
82
115
  }
83
116
  }
84
- if (typeof text == "string") {
85
- // Remove trailing blanks
86
- while (text && (text.endsWith(' ') || text.endsWith('\n') || text.endsWith('\r') || text.endsWith('\t')))
87
- text = text.substring(0, text.length - 1);
88
-
89
- // Hide session tokens
90
- text = this._removeBetween(text, "<Cookie>__sessiontoken=", "</Cookie>");
91
- text = this._removeBetween(text, "<X-Security-Token>", "</X-Security-Token>");
92
- text = this._removeBetween(text, '<sessiontoken xsi:type="xsd:string">', '</sessiontoken>');
93
- text = this._removeBetween(text, "<pstrSessionToken xsi:type='xsd:string'>", "</pstrSessionToken>");
94
- text = this._removeBetween(text, "<pstrSecurityToken xsi:type='xsd:string'>", "</pstrSecurityToken>");
95
- }
96
- return text;
117
+ else
118
+ obj[p] = Util.trim(obj[p]);
97
119
  }
120
+ }
121
+ if (typeof obj == "string") {
122
+ // Remove trailing blanks
123
+ while (obj && (obj.endsWith(' ') || obj.endsWith('\n') || obj.endsWith('\r') || obj.endsWith('\t')))
124
+ obj = obj.substring(0, obj.length - 1);
98
125
 
126
+ // Hide session tokens
127
+ obj = this._removeBetween(obj, "<Cookie>__sessiontoken=", "</Cookie>");
128
+ obj = this._removeBetween(obj, "<X-Security-Token>", "</X-Security-Token>");
129
+ obj = this._removeBetween(obj, '<sessiontoken xsi:type="xsd:string">', '</sessiontoken>');
130
+ obj = this._removeBetween(obj, "<pstrSessionToken xsi:type='xsd:string'>", "</pstrSessionToken>");
131
+ obj = this._removeBetween(obj, "<pstrSecurityToken xsi:type='xsd:string'>", "</pstrSecurityToken>");
132
+ obj = this._removeBetween(obj, '<password xsi:type="xsd:string">', '</password>');
133
+ }
134
+ return obj;
135
+ }
99
136
  }
100
137
 
101
138
  // Public expots
102
139
  exports.Util = Util;
140
+
141
+ })();
package/src/xtkCaster.js CHANGED
@@ -1,4 +1,3 @@
1
- "use strict";
2
1
  /*
3
2
  Copyright 2020 Adobe. All rights reserved.
4
3
  This file is licensed to you under the Apache License, Version 2.0 (the "License");
@@ -10,7 +9,8 @@ the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR REPRESENTA
10
9
  OF ANY KIND, either express or implied. See the License for the specific language
11
10
  governing permissions and limitations under the License.
12
11
  */
13
-
12
+ (function() {
13
+ "use strict";
14
14
 
15
15
  /**********************************************************************************
16
16
  *
@@ -56,15 +56,16 @@ governing permissions and limitations under the License.
56
56
  * @memberof Campaign
57
57
  */
58
58
 
59
- /**
60
- * Helpers to convert between JavaScript data types and Campaign XTK data types
61
- *
59
+ /**
62
60
  * @memberof Campaign
63
61
  * @class
64
62
  * @constructor
65
63
  */
66
64
  class XtkCaster {
67
65
 
66
+ /**
67
+ * Helpers to convert between JavaScript data types and Campaign XTK data types
68
+ */
68
69
  constructor() {
69
70
  }
70
71
 
@@ -111,7 +112,7 @@ class XtkCaster {
111
112
  case "datetimenotz":
112
113
  case 10: // FIELD_DATE
113
114
  case "date":
114
- return "timeStampValue"
115
+ return "timeStampValue";
115
116
  default: {
116
117
  throw CampaignException.BAD_PARAMETER("type", type, `Cannot get variant storage attribute name for type '${type}'`);
117
118
  }
@@ -371,3 +372,5 @@ class XtkCaster {
371
372
  }
372
373
 
373
374
  exports.XtkCaster = XtkCaster;
375
+
376
+ })();
@@ -1,4 +1,3 @@
1
- "use strict";
2
1
  /*
3
2
  Copyright 2020 Adobe. All rights reserved.
4
3
  This file is licensed to you under the Apache License, Version 2.0 (the "License");
@@ -10,7 +9,11 @@ the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR REPRESENTA
10
9
  OF ANY KIND, either express or implied. See the License for the specific language
11
10
  governing permissions and limitations under the License.
12
11
  */
12
+ (function() {
13
+ "use strict";
14
+
13
15
  const DomUtil = require('./domUtil.js').DomUtil;
16
+ const { Cache } = require('./cache.js');
14
17
 
15
18
 
16
19
  /**********************************************************************************
@@ -19,14 +22,40 @@ const DomUtil = require('./domUtil.js').DomUtil;
19
22
  *
20
23
  *********************************************************************************/
21
24
 
22
- function entityKey(entityType, entityFullName) {
23
- return entityType + "|" + entityFullName;
24
- }
25
-
26
- class XtkEntityCache {
25
+ /**
26
+ * @private
27
+ * @class
28
+ * @constructor
29
+ * @memberof Campaign
30
+ */
31
+ class XtkEntityCache extends Cache {
27
32
 
28
- constructor() {
29
- this.cache = {}
33
+ /**
34
+ * A in-memory cache for xtk entities. Not intended to be used directly,
35
+ * but an internal cache for the Campaign.Client object.
36
+ *
37
+ * Cached object are made of
38
+ * - the key is a string in the form <entityType>|<entityName>, such as "xtk:schema|nms:recipient"
39
+ * - the value is a DOM element corresponding to the entity. It's always a DOM element, regardless of the client representation
40
+ *
41
+ * @param {Storage} storage is an optional Storage object, such as localStorage or sessionStorage
42
+ * @param {string} rootKey is an optional root key to use for the storage object
43
+ * @param {number} ttl is the TTL for objects in ms. Defaults to 5 mins
44
+ */
45
+ constructor(storage, rootKey, ttl) {
46
+ super(storage, rootKey, ttl, (entityType, entityFullName) => entityType + "|" + entityFullName, (item, serDeser) => {
47
+ if (serDeser) {
48
+ if (!item || !item.value) throw Error(`Cannot serialize falsy cached item`);
49
+ const value = Object.assign({}, item);
50
+ value.value = DomUtil.toXMLString(item.value);
51
+ return JSON.stringify(value);
52
+ }
53
+ else {
54
+ const json = JSON.parse(item);
55
+ json.value = DomUtil.parse(json.value).documentElement;
56
+ return json;
57
+ }
58
+ });
30
59
  }
31
60
 
32
61
  /**
@@ -36,9 +65,7 @@ class XtkEntityCache {
36
65
  * @returns {*} the cached entity, or undefined if not found
37
66
  */
38
67
  get(entityType, entityFullName) {
39
- const key = entityKey(entityType, entityFullName);
40
- var entity = this.cache[key]
41
- return entity;
68
+ return super.get(entityType, entityFullName);
42
69
  }
43
70
 
44
71
  /**
@@ -48,31 +75,22 @@ class XtkEntityCache {
48
75
  * @param {*} entity is the entity
49
76
  */
50
77
  put(entityType, entityFullName, entity) {
51
- var key = entityKey(entityType, entityFullName);
52
- this.cache[key] = entity;
53
-
78
+ super.put(entityType, entityFullName, entity);
54
79
  // For schemas, cache interfaces
55
80
  if (entityType == "xtk:schema") {
56
81
  const namespace = entity.getAttribute("namespace");
57
82
  var interfaceElement = DomUtil.getFirstChildElement(entity, "interface");
58
83
  while (interfaceElement) {
59
84
  const name = `${namespace}:${interfaceElement.getAttribute("name")}`;
60
- const key = entityKey(entityType, name);
61
- this.cache[key] = interfaceElement;
85
+ super.put(entityType, name, interfaceElement);
62
86
  interfaceElement = DomUtil.getNextSiblingElement(interfaceElement, "interface");
63
87
  }
64
88
  }
65
89
  }
66
-
67
- /**
68
- * Clears the cache
69
- */
70
- clear() {
71
- this.cache = {};
72
- }
73
-
74
90
  }
75
91
 
76
92
 
77
93
  // Public exports
78
94
  exports.XtkEntityCache = XtkEntityCache;
95
+
96
+ })();