@getuserfeedback/adapters 0.3.0 → 0.4.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/README.md +135 -0
- package/dist/gtm/core.d.ts.map +1 -1
- package/dist/gtm/core.js +11 -8
- package/dist/gtm/index.d.ts +1 -1
- package/dist/gtm/index.d.ts.map +1 -1
- package/dist/gtm/index.js +1 -1
- package/dist/gtm/template-generation.d.ts +57 -7
- package/dist/gtm/template-generation.d.ts.map +1 -1
- package/dist/gtm/template-generation.js +266 -127
- package/package.json +1 -1
package/README.md
ADDED
|
@@ -0,0 +1,135 @@
|
|
|
1
|
+
# `@getuserfeedback/adapters`
|
|
2
|
+
|
|
3
|
+
`@getuserfeedback/adapters` publishes external-system translation layers built on top of the public widget protocol.
|
|
4
|
+
|
|
5
|
+
## GTM
|
|
6
|
+
|
|
7
|
+
The `@getuserfeedback/adapters/gtm` entrypoint is the authoritative source for Google Tag Manager template generation. It owns:
|
|
8
|
+
|
|
9
|
+
- GTM consent mapping logic
|
|
10
|
+
- GTM theme normalization logic
|
|
11
|
+
- GTM template parameter generation
|
|
12
|
+
- GTM runtime source generation
|
|
13
|
+
- GTM permission generation
|
|
14
|
+
- GTM template defaults, help text, and option labels
|
|
15
|
+
- the canonical loader script base URL pattern
|
|
16
|
+
|
|
17
|
+
### Public exports
|
|
18
|
+
|
|
19
|
+
Core mappings:
|
|
20
|
+
|
|
21
|
+
- `GTM_CONSENT_TYPES`
|
|
22
|
+
- `ESSENTIAL_GTM_SCOPES`
|
|
23
|
+
- `DEFAULT_GTM_SCOPE_MAPPINGS`
|
|
24
|
+
- `GTM_TEMPLATE_SCOPE_OPTIONS`
|
|
25
|
+
- `GTM_TEMPLATE_MAPPING_OPTIONS`
|
|
26
|
+
- `isGtmConsentType(value)`
|
|
27
|
+
- `isHostConfigurableGtmScope(scope)`
|
|
28
|
+
- `normalizeGtmThemeInput(input)`
|
|
29
|
+
- `resolveDefaultConsentFromGtm(input)`
|
|
30
|
+
- `buildInitOptionsFromGtmTemplate(input)`
|
|
31
|
+
|
|
32
|
+
Types:
|
|
33
|
+
|
|
34
|
+
- `GtmConsentType`
|
|
35
|
+
- `GtmConsentValue`
|
|
36
|
+
- `GtmConsentState`
|
|
37
|
+
- `GtmScopeMapping`
|
|
38
|
+
- `GtmAnalyticsMeasurementMode`
|
|
39
|
+
- `GtmTemplateInput`
|
|
40
|
+
- `GtmTemplateScopeOption`
|
|
41
|
+
- `GtmTemplateMappingOption`
|
|
42
|
+
|
|
43
|
+
Template generation:
|
|
44
|
+
|
|
45
|
+
- `DEFAULT_GTM_LOADER_SCRIPT_BASE_URL`
|
|
46
|
+
- `buildGtmTemplateParameters(options?)`
|
|
47
|
+
- `buildGtmRuntimeSource(options?)`
|
|
48
|
+
- `buildGtmPermissions(options?)`
|
|
49
|
+
- `buildGtmTemplateInfo(options?)`
|
|
50
|
+
- `buildGtmTemplateParts(options?)`
|
|
51
|
+
- `buildGtmTemplateArtifact(options?)`
|
|
52
|
+
|
|
53
|
+
### Essential scope policy
|
|
54
|
+
|
|
55
|
+
`functionality.storage` and `security.storage` are essential baseline scopes.
|
|
56
|
+
|
|
57
|
+
- They remain accepted by the protocol for backward compatibility.
|
|
58
|
+
- They are not host-configurable in GTM-generated consent UI.
|
|
59
|
+
- They are not emitted in GTM-generated host-overridable default consent output.
|
|
60
|
+
- Generated help text states that they are fixed by the loader.
|
|
61
|
+
|
|
62
|
+
### Analytics measurement policy
|
|
63
|
+
|
|
64
|
+
Automatic GTM consent mode exposes an explicit analytics measurement policy:
|
|
65
|
+
|
|
66
|
+
- `inherit-analytics-storage`
|
|
67
|
+
- `granted`
|
|
68
|
+
- `denied`
|
|
69
|
+
|
|
70
|
+
Manual GTM consent mode does not apply hidden analytics measurement behavior. It only uses the generated host-configurable scope mappings.
|
|
71
|
+
|
|
72
|
+
### Theme behavior
|
|
73
|
+
|
|
74
|
+
Generated GTM theme support accepts:
|
|
75
|
+
|
|
76
|
+
- fixed `light`
|
|
77
|
+
- fixed `dark`
|
|
78
|
+
- fixed `system`
|
|
79
|
+
- host-sync via protocol auto-detect attributes
|
|
80
|
+
- GTM variable-driven values
|
|
81
|
+
- comma-separated auto-detect attribute lists
|
|
82
|
+
|
|
83
|
+
The adapter normalizes all theme inputs into protocol-valid `colorScheme`.
|
|
84
|
+
|
|
85
|
+
### Generate a GTM template artifact
|
|
86
|
+
|
|
87
|
+
```ts
|
|
88
|
+
import { buildGtmTemplateArtifact } from "@getuserfeedback/adapters/gtm";
|
|
89
|
+
|
|
90
|
+
const artifact = buildGtmTemplateArtifact({
|
|
91
|
+
loaderScriptBaseUrl: "https://cdn.getuserfeedback.com/widget/loader/v1",
|
|
92
|
+
});
|
|
93
|
+
|
|
94
|
+
artifact.info;
|
|
95
|
+
artifact.parameters;
|
|
96
|
+
artifact.runtimeSource;
|
|
97
|
+
artifact.permissions;
|
|
98
|
+
```
|
|
99
|
+
|
|
100
|
+
The returned object is suitable for rendering into GTM `___INFO___`, `___TEMPLATE_PARAMETERS___`, `___SANDBOXED_JS_FOR_WEB_TEMPLATE___`, and `___WEB_PERMISSIONS___` sections.
|
|
101
|
+
|
|
102
|
+
### What the GTM repo should still own
|
|
103
|
+
|
|
104
|
+
After importing the published package, the GTM repo should only own:
|
|
105
|
+
|
|
106
|
+
- GTM Gallery wrapper file assembly
|
|
107
|
+
- brand thumbnail and base64 image assets
|
|
108
|
+
- `metadata.yaml`
|
|
109
|
+
- publishing and release workflow
|
|
110
|
+
|
|
111
|
+
It should not rebuild parameters, runtime source, permissions, or GTM-specific init payload translation.
|
|
112
|
+
|
|
113
|
+
### Customizing the loader base URL
|
|
114
|
+
|
|
115
|
+
Pass `loaderScriptBaseUrl` to:
|
|
116
|
+
|
|
117
|
+
- `buildGtmRuntimeSource`
|
|
118
|
+
- `buildGtmPermissions`
|
|
119
|
+
- `buildGtmTemplateParts`
|
|
120
|
+
- `buildGtmTemplateArtifact`
|
|
121
|
+
|
|
122
|
+
The same base URL is used to derive the runtime loader URL and the `inject_script` permission pattern.
|
|
123
|
+
|
|
124
|
+
### Versioning expectations
|
|
125
|
+
|
|
126
|
+
Any change that affects generated GTM output is a public package change and should be versioned accordingly. This includes:
|
|
127
|
+
|
|
128
|
+
- parameter shape or defaults
|
|
129
|
+
- runtime behavior
|
|
130
|
+
- permission generation
|
|
131
|
+
- default mappings
|
|
132
|
+
- essential-scope exposure
|
|
133
|
+
- analytics measurement behavior
|
|
134
|
+
|
|
135
|
+
Release notes should call out template-affecting changes explicitly.
|
package/dist/gtm/core.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"core.d.ts","sourceRoot":"","sources":["../../src/gtm/core.ts"],"names":[],"mappings":"AAAA,OAAO,
|
|
1
|
+
{"version":3,"file":"core.d.ts","sourceRoot":"","sources":["../../src/gtm/core.ts"],"names":[],"mappings":"AAAA,OAAO,EAIN,KAAK,WAAW,EAGhB,KAAK,KAAK,EACV,MAAM,2BAA2B,CAAC;AAEnC,eAAO,MAAM,iBAAiB,EAAE,SAAS;IACxC,uBAAuB;IACvB,kBAAkB;IAClB,mBAAmB;IACnB,yBAAyB;IACzB,YAAY;IACZ,cAAc;IACd,oBAAoB;CASpB,CAAC;AAEF,MAAM,MAAM,cAAc,GAAG,CAAC,OAAO,iBAAiB,CAAC,CAAC,MAAM,CAAC,CAAC;AAEhE,MAAM,MAAM,eAAe,GAAG,SAAS,GAAG,QAAQ,CAAC;AAEnD,MAAM,MAAM,2BAA2B,GACpC,2BAA2B,GAC3B,SAAS,GACT,QAAQ,CAAC;AAEZ,MAAM,MAAM,eAAe,GAAG;IAC7B,KAAK,EAAE,KAAK,CAAC;IACb,WAAW,EAAE,cAAc,CAAC;CAC5B,CAAC;AAEF,MAAM,MAAM,eAAe,GAAG,OAAO,CAAC,MAAM,CAAC,cAAc,EAAE,eAAe,CAAC,CAAC,CAAC;AAE/E,MAAM,MAAM,gBAAgB,GAAG;IAC9B,MAAM,EAAE,MAAM,CAAC;IACf,YAAY,CAAC,EAAE,eAAe,CAAC;IAC/B,aAAa,CAAC,EAAE,aAAa,CAAC,eAAe,CAAC,CAAC;IAC/C,wBAAwB,CAAC,EAAE,2BAA2B,CAAC;IACvD,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,gBAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B,WAAW,CAAC,EAAE,WAAW,CAAC,aAAa,CAAC,CAAC;IACzC,YAAY,CAAC,EAAE,WAAW,CAAC,cAAc,CAAC,CAAC;IAC3C,gBAAgB,CAAC,EAAE,WAAW,CAAC,kBAAkB,CAAC,CAAC;IACnD,UAAU,CAAC,EAAE,WAAW,CAAC,YAAY,CAAC,CAAC;CACvC,CAAC;AAEF,KAAK,oBAAoB,GAAG,WAAW,CACtC,OAAO,CAAC,WAAW,CAAC,gBAAgB,CAAC,EAAE,MAAM,CAAC,CAC9C,CAAC,MAAM,CAAC,CAAC;AAEV,MAAM,MAAM,sBAAsB,GAAG;IACpC,KAAK,EAAE,MAAM,CAAC;IACd,KAAK,EAAE,KAAK,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;CACpB,CAAC;AAEF,MAAM,MAAM,wBAAwB,GAAG;IACtC,WAAW,EAAE,cAAc,CAAC;IAC5B,KAAK,EAAE,MAAM,CAAC;CACd,CAAC;AAEF,eAAO,MAAM,oBAAoB,EAAE,SAAS;IAC3C,uBAAuB;IACvB,kBAAkB;CAC8B,CAAC;AAIlD,eAAO,MAAM,0BAA0B,GACtC,OAAO,KAAK,KACV,KAAK,IAAI,oBAAmD,CAAC;AAEhE,eAAO,MAAM,0BAA0B,EAAE,aAAa,CAAC,eAAe,CA6BrE,CAAC;AA4BF,eAAO,MAAM,0BAA0B,EAAE,aAAa,CAAC,sBAAsB,CAKzE,CAAC;AAEL,eAAO,MAAM,4BAA4B,EAAE,aAAa,CAAC,wBAAwB,CAI7E,CAAC;AAEL,wBAAgB,gBAAgB,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,IAAI,cAAc,CAKxE;AAED,wBAAgB,sBAAsB,CACrC,KAAK,EAAE,OAAO,GACZ,WAAW,CAAC,aAAa,CAAC,GAAG,SAAS,CA2CxC;AAED,wBAAgB,4BAA4B,CAAC,KAAK,EAAE;IACnD,YAAY,CAAC,EAAE,eAAe,CAAC;IAC/B,aAAa,CAAC,EAAE,aAAa,CAAC,eAAe,CAAC,CAAC;IAC/C,wBAAwB,CAAC,EAAE,2BAA2B,CAAC;CACvD,GAAG,WAAW,CAAC,gBAAgB,CAAC,GAAG,SAAS,CA6B5C;AAED,wBAAgB,+BAA+B,CAC9C,KAAK,EAAE,gBAAgB,GACrB,WAAW,CA8Bb"}
|
package/dist/gtm/core.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { DEFAULT_AUTO_DETECT_COLOR_SCHEME_ATTRS, listScopes, } from "@getuserfeedback/protocol";
|
|
1
|
+
import { colorSchemeConfigInputSchema, consentConfigInputSchema, DEFAULT_AUTO_DETECT_COLOR_SCHEME_ATTRS, listScopes, parseInitOptions, } from "@getuserfeedback/protocol";
|
|
2
2
|
export const GTM_CONSENT_TYPES = [
|
|
3
3
|
"functionality_storage",
|
|
4
4
|
"security_storage",
|
|
@@ -102,17 +102,17 @@ export function normalizeGtmThemeInput(input) {
|
|
|
102
102
|
return normalized;
|
|
103
103
|
}
|
|
104
104
|
if (normalized === "auto") {
|
|
105
|
-
return {
|
|
105
|
+
return colorSchemeConfigInputSchema.parse({
|
|
106
106
|
autoDetectColorScheme: [...DEFAULT_AUTO_DETECT_COLOR_SCHEME_ATTRS],
|
|
107
|
-
};
|
|
107
|
+
});
|
|
108
108
|
}
|
|
109
109
|
const attrs = normalizeAttrList(input);
|
|
110
110
|
if (attrs.length === 0) {
|
|
111
111
|
return undefined;
|
|
112
112
|
}
|
|
113
|
-
return {
|
|
113
|
+
return colorSchemeConfigInputSchema.parse({
|
|
114
114
|
autoDetectColorScheme: attrs,
|
|
115
|
-
};
|
|
115
|
+
});
|
|
116
116
|
}
|
|
117
117
|
export function resolveDefaultConsentFromGtm(input) {
|
|
118
118
|
const consentState = input.consentState;
|
|
@@ -129,7 +129,10 @@ export function resolveDefaultConsentFromGtm(input) {
|
|
|
129
129
|
consentState.analytics_storage === "granted") {
|
|
130
130
|
grantedScopes.push("analytics.measurement");
|
|
131
131
|
}
|
|
132
|
-
|
|
132
|
+
const normalizedGrantedScopes = uniqueScopes(grantedScopes);
|
|
133
|
+
return normalizedGrantedScopes.length > 0
|
|
134
|
+
? consentConfigInputSchema.parse(normalizedGrantedScopes)
|
|
135
|
+
: undefined;
|
|
133
136
|
}
|
|
134
137
|
export function buildInitOptionsFromGtmTemplate(input) {
|
|
135
138
|
const colorScheme = normalizeGtmThemeInput(input.colorScheme);
|
|
@@ -138,7 +141,7 @@ export function buildInitOptionsFromGtmTemplate(input) {
|
|
|
138
141
|
scopeMappings: input.scopeMappings,
|
|
139
142
|
analyticsMeasurementMode: input.analyticsMeasurementMode,
|
|
140
143
|
});
|
|
141
|
-
return {
|
|
144
|
+
return parseInitOptions({
|
|
142
145
|
apiKey: input.apiKey,
|
|
143
146
|
...(colorScheme !== undefined ? { colorScheme } : {}),
|
|
144
147
|
...(input.disableTelemetry !== undefined
|
|
@@ -159,5 +162,5 @@ export function buildInitOptionsFromGtmTemplate(input) {
|
|
|
159
162
|
...(input.runtimeEndpoints !== undefined
|
|
160
163
|
? { runtimeEndpoints: input.runtimeEndpoints }
|
|
161
164
|
: {}),
|
|
162
|
-
};
|
|
165
|
+
});
|
|
163
166
|
}
|
package/dist/gtm/index.d.ts
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
export { buildInitOptionsFromGtmTemplate, DEFAULT_GTM_SCOPE_MAPPINGS, ESSENTIAL_GTM_SCOPES, GTM_CONSENT_TYPES, GTM_TEMPLATE_MAPPING_OPTIONS, GTM_TEMPLATE_SCOPE_OPTIONS, type GtmAnalyticsMeasurementMode, type GtmConsentState, type GtmConsentType, type GtmConsentValue, type GtmScopeMapping, type GtmTemplateInput, type GtmTemplateMappingOption, type GtmTemplateScopeOption, isGtmConsentType, isHostConfigurableGtmScope, normalizeGtmThemeInput, resolveDefaultConsentFromGtm, } from "./core.js";
|
|
2
|
-
export { buildGtmRuntimeSource, buildGtmTemplateParameters, buildGtmTemplateParts, DEFAULT_GTM_LOADER_SCRIPT_BASE_URL, type GtmTemplateParts, type TemplateCondition, type TemplateParameter, type TemplateSelectItem, type TemplateValueValidator, } from "./template-generation.js";
|
|
2
|
+
export { buildGtmPermissions, buildGtmRuntimeSource, buildGtmTemplateArtifact, buildGtmTemplateInfo, buildGtmTemplateParameters, buildGtmTemplateParts, DEFAULT_GTM_LOADER_SCRIPT_BASE_URL, type GtmTemplateArtifact, type GtmTemplateGenerationOptions, type GtmTemplateInfo, type GtmTemplateParts, type GtmTemplatePermission, type TemplateCondition, type TemplateParameter, type TemplateSelectItem, type TemplateValueValidator, } from "./template-generation.js";
|
|
3
3
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/gtm/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/gtm/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACN,+BAA+B,EAC/B,0BAA0B,EAC1B,oBAAoB,EACpB,iBAAiB,EACjB,4BAA4B,EAC5B,0BAA0B,EAC1B,KAAK,2BAA2B,EAChC,KAAK,eAAe,EACpB,KAAK,cAAc,EACnB,KAAK,eAAe,EACpB,KAAK,eAAe,EACpB,KAAK,gBAAgB,EACrB,KAAK,wBAAwB,EAC7B,KAAK,sBAAsB,EAC3B,gBAAgB,EAChB,0BAA0B,EAC1B,sBAAsB,EACtB,4BAA4B,GAC5B,MAAM,WAAW,CAAC;AACnB,OAAO,EACN,qBAAqB,EACrB,0BAA0B,EAC1B,qBAAqB,EACrB,kCAAkC,EAClC,KAAK,gBAAgB,EACrB,KAAK,iBAAiB,EACtB,KAAK,iBAAiB,EACtB,KAAK,kBAAkB,EACvB,KAAK,sBAAsB,GAC3B,MAAM,0BAA0B,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/gtm/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACN,+BAA+B,EAC/B,0BAA0B,EAC1B,oBAAoB,EACpB,iBAAiB,EACjB,4BAA4B,EAC5B,0BAA0B,EAC1B,KAAK,2BAA2B,EAChC,KAAK,eAAe,EACpB,KAAK,cAAc,EACnB,KAAK,eAAe,EACpB,KAAK,eAAe,EACpB,KAAK,gBAAgB,EACrB,KAAK,wBAAwB,EAC7B,KAAK,sBAAsB,EAC3B,gBAAgB,EAChB,0BAA0B,EAC1B,sBAAsB,EACtB,4BAA4B,GAC5B,MAAM,WAAW,CAAC;AACnB,OAAO,EACN,mBAAmB,EACnB,qBAAqB,EACrB,wBAAwB,EACxB,oBAAoB,EACpB,0BAA0B,EAC1B,qBAAqB,EACrB,kCAAkC,EAClC,KAAK,mBAAmB,EACxB,KAAK,4BAA4B,EACjC,KAAK,eAAe,EACpB,KAAK,gBAAgB,EACrB,KAAK,qBAAqB,EAC1B,KAAK,iBAAiB,EACtB,KAAK,iBAAiB,EACtB,KAAK,kBAAkB,EACvB,KAAK,sBAAsB,GAC3B,MAAM,0BAA0B,CAAC"}
|
package/dist/gtm/index.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
export { buildInitOptionsFromGtmTemplate, DEFAULT_GTM_SCOPE_MAPPINGS, ESSENTIAL_GTM_SCOPES, GTM_CONSENT_TYPES, GTM_TEMPLATE_MAPPING_OPTIONS, GTM_TEMPLATE_SCOPE_OPTIONS, isGtmConsentType, isHostConfigurableGtmScope, normalizeGtmThemeInput, resolveDefaultConsentFromGtm, } from "./core.js";
|
|
2
|
-
export { buildGtmRuntimeSource, buildGtmTemplateParameters, buildGtmTemplateParts, DEFAULT_GTM_LOADER_SCRIPT_BASE_URL, } from "./template-generation.js";
|
|
2
|
+
export { buildGtmPermissions, buildGtmRuntimeSource, buildGtmTemplateArtifact, buildGtmTemplateInfo, buildGtmTemplateParameters, buildGtmTemplateParts, DEFAULT_GTM_LOADER_SCRIPT_BASE_URL, } from "./template-generation.js";
|
|
@@ -64,16 +64,66 @@ export type TemplateParameter = {
|
|
|
64
64
|
groupStyle: "ZIPPY_CLOSED";
|
|
65
65
|
subParams: TemplateParameter[];
|
|
66
66
|
};
|
|
67
|
+
type GtmPermissionStringValue = {
|
|
68
|
+
type: 1;
|
|
69
|
+
string: string;
|
|
70
|
+
};
|
|
71
|
+
type GtmPermissionBooleanValue = {
|
|
72
|
+
type: 8;
|
|
73
|
+
boolean: boolean;
|
|
74
|
+
};
|
|
75
|
+
type GtmPermissionMapValue = {
|
|
76
|
+
type: 3;
|
|
77
|
+
mapKey: GtmPermissionStringValue[];
|
|
78
|
+
mapValue: Array<GtmPermissionStringValue | GtmPermissionBooleanValue | GtmPermissionListValue | GtmPermissionMapValue>;
|
|
79
|
+
};
|
|
80
|
+
type GtmPermissionListValue = {
|
|
81
|
+
type: 2;
|
|
82
|
+
listItem: Array<GtmPermissionStringValue | GtmPermissionBooleanValue | GtmPermissionMapValue>;
|
|
83
|
+
};
|
|
84
|
+
type GtmPermissionParam = {
|
|
85
|
+
key: string;
|
|
86
|
+
value: GtmPermissionStringValue | GtmPermissionBooleanValue | GtmPermissionListValue | GtmPermissionMapValue;
|
|
87
|
+
};
|
|
88
|
+
export type GtmTemplatePermission = {
|
|
89
|
+
instance: {
|
|
90
|
+
key: {
|
|
91
|
+
publicId: string;
|
|
92
|
+
versionId: "1";
|
|
93
|
+
};
|
|
94
|
+
param: GtmPermissionParam[];
|
|
95
|
+
};
|
|
96
|
+
clientAnnotations?: {
|
|
97
|
+
isEditedByUser: true;
|
|
98
|
+
};
|
|
99
|
+
isRequired: true;
|
|
100
|
+
};
|
|
101
|
+
export type GtmTemplateInfo = {
|
|
102
|
+
type: "TAG";
|
|
103
|
+
version: 1;
|
|
104
|
+
displayName: string;
|
|
105
|
+
description: string;
|
|
106
|
+
categories: readonly ["SURVEY", "PERSONALIZATION", "UTILITY"];
|
|
107
|
+
containerContexts: readonly ["WEB"];
|
|
108
|
+
};
|
|
67
109
|
export type GtmTemplateParts = {
|
|
110
|
+
info: GtmTemplateInfo;
|
|
68
111
|
parameters: TemplateParameter[];
|
|
69
112
|
runtimeSource: string;
|
|
113
|
+
permissions: GtmTemplatePermission[];
|
|
70
114
|
};
|
|
71
|
-
export
|
|
72
|
-
export
|
|
73
|
-
export declare function buildGtmRuntimeSource(input?: {
|
|
115
|
+
export type GtmTemplateArtifact = GtmTemplateParts;
|
|
116
|
+
export type GtmTemplateGenerationOptions = {
|
|
74
117
|
loaderScriptBaseUrl?: string;
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
118
|
+
displayName?: string;
|
|
119
|
+
description?: string;
|
|
120
|
+
};
|
|
121
|
+
export declare const DEFAULT_GTM_LOADER_SCRIPT_BASE_URL = "https://cdn.getuserfeedback.com/widget/loader/v1";
|
|
122
|
+
export declare function buildGtmTemplateParameters(_options?: GtmTemplateGenerationOptions): TemplateParameter[];
|
|
123
|
+
export declare function buildGtmRuntimeSource(input?: GtmTemplateGenerationOptions): string;
|
|
124
|
+
export declare function buildGtmPermissions(input?: GtmTemplateGenerationOptions): GtmTemplatePermission[];
|
|
125
|
+
export declare function buildGtmTemplateInfo(input?: GtmTemplateGenerationOptions): GtmTemplateInfo;
|
|
126
|
+
export declare function buildGtmTemplateParts(input?: GtmTemplateGenerationOptions): GtmTemplateParts;
|
|
127
|
+
export declare function buildGtmTemplateArtifact(input?: GtmTemplateGenerationOptions): GtmTemplateArtifact;
|
|
128
|
+
export {};
|
|
79
129
|
//# sourceMappingURL=template-generation.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"template-generation.d.ts","sourceRoot":"","sources":["../../src/gtm/template-generation.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"template-generation.d.ts","sourceRoot":"","sources":["../../src/gtm/template-generation.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,36 +1,47 @@
|
|
|
1
1
|
import { DEFAULT_AUTO_DETECT_COLOR_SCHEME_ATTRS, } from "@getuserfeedback/protocol";
|
|
2
|
-
import { GTM_CONSENT_TYPES, GTM_TEMPLATE_MAPPING_OPTIONS, GTM_TEMPLATE_SCOPE_OPTIONS, isHostConfigurableGtmScope, } from "./core.js";
|
|
2
|
+
import { DEFAULT_GTM_SCOPE_MAPPINGS, ESSENTIAL_GTM_SCOPES, GTM_CONSENT_TYPES, GTM_TEMPLATE_MAPPING_OPTIONS, GTM_TEMPLATE_SCOPE_OPTIONS, isHostConfigurableGtmScope, } from "./core.js";
|
|
3
3
|
export const DEFAULT_GTM_LOADER_SCRIPT_BASE_URL = "https://cdn.getuserfeedback.com/widget/loader/v1";
|
|
4
|
+
const GTM_TEMPLATE_VERSION = 1;
|
|
5
|
+
const GTM_TEMPLATE_DEFAULT_DISPLAY_NAME = "getuserfeedback Widget";
|
|
6
|
+
const GTM_TEMPLATE_DEFAULT_DESCRIPTION = "Load the getuserfeedback widget with modern loader, theme, and GTM Consent Mode defaults derived from the public protocol contract.";
|
|
7
|
+
const GTM_TEMPLATE_CATEGORIES = [
|
|
8
|
+
"SURVEY",
|
|
9
|
+
"PERSONALIZATION",
|
|
10
|
+
"UTILITY",
|
|
11
|
+
];
|
|
12
|
+
const GTM_TEMPLATE_CONTAINER_CONTEXTS = ["WEB"];
|
|
13
|
+
const GTM_QUEUE_KEY = "__getuserfeedback_queue";
|
|
4
14
|
const NON_EMPTY_VALIDATOR = { type: "NON_EMPTY" };
|
|
5
|
-
const
|
|
6
|
-
.map((option) => `${option.label}: ${option.description}`)
|
|
7
|
-
.join("\n");
|
|
8
|
-
const buildDefaultTemplateScopeMappings = () => [
|
|
9
|
-
{
|
|
10
|
-
scope: "analytics.storage",
|
|
11
|
-
mapping: "analytics_storage",
|
|
12
|
-
},
|
|
13
|
-
{
|
|
14
|
-
scope: "analytics.measurement",
|
|
15
|
-
mapping: "analytics_storage",
|
|
16
|
-
},
|
|
17
|
-
{
|
|
18
|
-
scope: "personalization.storage",
|
|
19
|
-
mapping: "personalization_storage",
|
|
20
|
-
},
|
|
15
|
+
const MANUAL_CONSENT_MODE_CONDITION = [
|
|
21
16
|
{
|
|
22
|
-
|
|
23
|
-
|
|
17
|
+
paramName: "consentMode",
|
|
18
|
+
paramValue: "manual",
|
|
19
|
+
type: "EQUALS",
|
|
24
20
|
},
|
|
21
|
+
];
|
|
22
|
+
const AUTOMATIC_CONSENT_MODE_CONDITION = [
|
|
25
23
|
{
|
|
26
|
-
|
|
27
|
-
|
|
24
|
+
paramName: "consentMode",
|
|
25
|
+
paramValue: "automatic",
|
|
26
|
+
type: "EQUALS",
|
|
28
27
|
},
|
|
28
|
+
];
|
|
29
|
+
const buildHostConfigurableDefaultScopeMappings = () => [
|
|
30
|
+
...DEFAULT_GTM_SCOPE_MAPPINGS.filter((mapping) => isHostConfigurableGtmScope(mapping.scope)).map((mapping) => ({
|
|
31
|
+
scope: mapping.scope,
|
|
32
|
+
mapping: mapping.consentType,
|
|
33
|
+
})),
|
|
29
34
|
{
|
|
30
|
-
scope: "
|
|
31
|
-
mapping: "
|
|
35
|
+
scope: "analytics.measurement",
|
|
36
|
+
mapping: "analytics_storage",
|
|
32
37
|
},
|
|
33
38
|
];
|
|
39
|
+
const buildScopeParameterHelp = () => [
|
|
40
|
+
"Essential scopes are fixed by the loader and are not exposed for GTM override.",
|
|
41
|
+
`${ESSENTIAL_GTM_SCOPES[0]} and ${ESSENTIAL_GTM_SCOPES[1]} always remain baseline scopes outside the GTM template UI.`,
|
|
42
|
+
"",
|
|
43
|
+
...GTM_TEMPLATE_SCOPE_OPTIONS.filter((option) => isHostConfigurableGtmScope(option.scope)).map((option) => `${option.label}: ${option.description}`),
|
|
44
|
+
].join("\n");
|
|
34
45
|
const buildHostConfigurableScopeSelectItems = () => GTM_TEMPLATE_SCOPE_OPTIONS.filter((option) => isHostConfigurableGtmScope(option.scope)).map((option) => ({
|
|
35
46
|
value: option.scope,
|
|
36
47
|
displayValue: option.label,
|
|
@@ -40,7 +51,45 @@ const buildGtmConsentTypeSelectItems = () => GTM_TEMPLATE_MAPPING_OPTIONS.map((o
|
|
|
40
51
|
displayValue: `${option.label} Granted`,
|
|
41
52
|
}));
|
|
42
53
|
const trimTrailingSlash = (value) => value.endsWith("/") ? value.slice(0, -1) : value;
|
|
43
|
-
|
|
54
|
+
const stringValue = (value) => ({
|
|
55
|
+
type: 1,
|
|
56
|
+
string: value,
|
|
57
|
+
});
|
|
58
|
+
const booleanValue = (value) => ({
|
|
59
|
+
type: 8,
|
|
60
|
+
boolean: value,
|
|
61
|
+
});
|
|
62
|
+
const listValue = (items) => ({
|
|
63
|
+
type: 2,
|
|
64
|
+
listItem: items,
|
|
65
|
+
});
|
|
66
|
+
const mapValue = (entries) => ({
|
|
67
|
+
type: 3,
|
|
68
|
+
mapKey: entries.map(([key]) => stringValue(key)),
|
|
69
|
+
mapValue: entries.map(([, value]) => {
|
|
70
|
+
if (typeof value === "string") {
|
|
71
|
+
return stringValue(value);
|
|
72
|
+
}
|
|
73
|
+
if (typeof value === "boolean") {
|
|
74
|
+
return booleanValue(value);
|
|
75
|
+
}
|
|
76
|
+
return value;
|
|
77
|
+
}),
|
|
78
|
+
});
|
|
79
|
+
const buildPermission = (publicId, params) => ({
|
|
80
|
+
instance: {
|
|
81
|
+
key: {
|
|
82
|
+
publicId,
|
|
83
|
+
versionId: "1",
|
|
84
|
+
},
|
|
85
|
+
param: params,
|
|
86
|
+
},
|
|
87
|
+
clientAnnotations: {
|
|
88
|
+
isEditedByUser: true,
|
|
89
|
+
},
|
|
90
|
+
isRequired: true,
|
|
91
|
+
});
|
|
92
|
+
export function buildGtmTemplateParameters(_options) {
|
|
44
93
|
const scopeHelp = buildScopeParameterHelp();
|
|
45
94
|
const scopeSelectItems = buildHostConfigurableScopeSelectItems();
|
|
46
95
|
const mappingSelectItems = buildGtmConsentTypeSelectItems();
|
|
@@ -50,7 +99,7 @@ export function buildGtmTemplateParameters() {
|
|
|
50
99
|
name: "apiKey",
|
|
51
100
|
displayName: "API Key",
|
|
52
101
|
simpleValueType: true,
|
|
53
|
-
help: "Find your API key in getuserfeedback.com under Settings
|
|
102
|
+
help: "Find your API key in getuserfeedback.com under Settings -> Widget.",
|
|
54
103
|
valueValidators: [NON_EMPTY_VALIDATOR],
|
|
55
104
|
},
|
|
56
105
|
{
|
|
@@ -79,16 +128,16 @@ export function buildGtmTemplateParameters() {
|
|
|
79
128
|
},
|
|
80
129
|
{
|
|
81
130
|
value: "host",
|
|
82
|
-
displayValue: "Sync With Host",
|
|
131
|
+
displayValue: "Sync With Host Attributes",
|
|
83
132
|
},
|
|
84
133
|
{
|
|
85
134
|
value: "variable",
|
|
86
|
-
displayValue: "Variable",
|
|
135
|
+
displayValue: "Resolve From GTM Variable",
|
|
87
136
|
},
|
|
88
137
|
],
|
|
89
138
|
simpleValueType: true,
|
|
90
139
|
defaultValue: "host",
|
|
91
|
-
help: "
|
|
140
|
+
help: "Generate protocol-valid `init.opts.colorScheme` using fixed modes, host auto-detect attributes, or a GTM variable.",
|
|
92
141
|
},
|
|
93
142
|
{
|
|
94
143
|
type: "SELECT",
|
|
@@ -113,7 +162,7 @@ export function buildGtmTemplateParameters() {
|
|
|
113
162
|
displayName: "Host Theme Attributes",
|
|
114
163
|
simpleValueType: true,
|
|
115
164
|
defaultValue: DEFAULT_AUTO_DETECT_COLOR_SCHEME_ATTRS.join(","),
|
|
116
|
-
help: "Comma-separated attributes to inspect on `<html>` or `<body>`
|
|
165
|
+
help: "Comma-separated attributes to inspect on `<html>` or `<body>` when syncing the widget to host theme state.",
|
|
117
166
|
enablingConditions: [
|
|
118
167
|
{
|
|
119
168
|
paramName: "themeMode",
|
|
@@ -138,17 +187,41 @@ export function buildGtmTemplateParameters() {
|
|
|
138
187
|
{
|
|
139
188
|
value: "automatic",
|
|
140
189
|
displayValue: "Automatic (Use GTM Consent Mode)",
|
|
141
|
-
help: "
|
|
190
|
+
help: "Read GTM consent mode via `isConsentGranted`, translate granted consent types into widget `defaultConsent`, and apply the explicit analytics measurement policy.",
|
|
142
191
|
},
|
|
143
192
|
{
|
|
144
193
|
value: "manual",
|
|
145
194
|
displayValue: "Manual (Map Public Scopes)",
|
|
146
|
-
help: "Override
|
|
195
|
+
help: "Override host-configurable widget consent scopes with explicit GTM consent mappings. Essential scopes remain fixed by the loader and are never configurable here.",
|
|
147
196
|
},
|
|
148
197
|
],
|
|
149
198
|
simpleValueType: true,
|
|
150
199
|
defaultValue: "automatic",
|
|
151
200
|
},
|
|
201
|
+
{
|
|
202
|
+
type: "SELECT",
|
|
203
|
+
name: "analyticsMeasurementMode",
|
|
204
|
+
displayName: "Analytics Measurement Policy",
|
|
205
|
+
macrosInSelect: false,
|
|
206
|
+
selectItems: [
|
|
207
|
+
{
|
|
208
|
+
value: "inherit-analytics-storage",
|
|
209
|
+
displayValue: "Inherit analytics_storage",
|
|
210
|
+
},
|
|
211
|
+
{
|
|
212
|
+
value: "granted",
|
|
213
|
+
displayValue: "Always granted",
|
|
214
|
+
},
|
|
215
|
+
{
|
|
216
|
+
value: "denied",
|
|
217
|
+
displayValue: "Always denied",
|
|
218
|
+
},
|
|
219
|
+
],
|
|
220
|
+
simpleValueType: true,
|
|
221
|
+
defaultValue: "inherit-analytics-storage",
|
|
222
|
+
help: "Controls whether `analytics.measurement` follows GTM `analytics_storage` or is forced on/off in automatic mode.",
|
|
223
|
+
enablingConditions: [...AUTOMATIC_CONSENT_MODE_CONDITION],
|
|
224
|
+
},
|
|
152
225
|
{
|
|
153
226
|
type: "SIMPLE_TABLE",
|
|
154
227
|
name: "scopeMappings",
|
|
@@ -172,16 +245,10 @@ export function buildGtmTemplateParameters() {
|
|
|
172
245
|
},
|
|
173
246
|
],
|
|
174
247
|
newRowButtonText: "Add Scope",
|
|
175
|
-
help:
|
|
176
|
-
enablingConditions: [
|
|
177
|
-
{
|
|
178
|
-
paramName: "consentMode",
|
|
179
|
-
paramValue: "manual",
|
|
180
|
-
type: "EQUALS",
|
|
181
|
-
},
|
|
182
|
-
],
|
|
248
|
+
help: scopeHelp,
|
|
249
|
+
enablingConditions: [...MANUAL_CONSENT_MODE_CONDITION],
|
|
183
250
|
valueValidators: [NON_EMPTY_VALIDATOR],
|
|
184
|
-
defaultValue:
|
|
251
|
+
defaultValue: buildHostConfigurableDefaultScopeMappings().map((row) => ({
|
|
185
252
|
scope: row.scope,
|
|
186
253
|
mapping: row.mapping,
|
|
187
254
|
})),
|
|
@@ -192,7 +259,7 @@ export function buildGtmTemplateParameters() {
|
|
|
192
259
|
}
|
|
193
260
|
export function buildGtmRuntimeSource(input) {
|
|
194
261
|
const loaderScriptBaseUrl = trimTrailingSlash(input?.loaderScriptBaseUrl ?? DEFAULT_GTM_LOADER_SCRIPT_BASE_URL);
|
|
195
|
-
const defaultTemplateScopeMappings =
|
|
262
|
+
const defaultTemplateScopeMappings = buildHostConfigurableDefaultScopeMappings();
|
|
196
263
|
return `
|
|
197
264
|
const log = require("logToConsole");
|
|
198
265
|
const injectScript = require("injectScript");
|
|
@@ -203,8 +270,9 @@ const isConsentGranted = require("isConsentGranted");
|
|
|
203
270
|
const loaderScriptBaseUrl = ${JSON.stringify(loaderScriptBaseUrl)};
|
|
204
271
|
const gtmConsentTypes = ${JSON.stringify(GTM_CONSENT_TYPES)};
|
|
205
272
|
const defaultScopeMappings = ${JSON.stringify(defaultTemplateScopeMappings)};
|
|
206
|
-
const hostConfigurableScopes = ${JSON.stringify(
|
|
273
|
+
const hostConfigurableScopes = ${JSON.stringify(defaultTemplateScopeMappings.map((row) => row.scope))};
|
|
207
274
|
const defaultAutoDetectColorSchemeAttrs = ${JSON.stringify(DEFAULT_AUTO_DETECT_COLOR_SCHEME_ATTRS)};
|
|
275
|
+
const queueKey = ${JSON.stringify(GTM_QUEUE_KEY)};
|
|
208
276
|
|
|
209
277
|
const trimString = function(value) {
|
|
210
278
|
return typeof value === "string" ? value.trim() : "";
|
|
@@ -221,13 +289,13 @@ const normalizeAttrList = function(value) {
|
|
|
221
289
|
});
|
|
222
290
|
};
|
|
223
291
|
|
|
224
|
-
const normalizeThemeInput = function(
|
|
225
|
-
if (
|
|
292
|
+
const normalizeThemeInput = function(inputValue) {
|
|
293
|
+
if (inputValue === undefined || inputValue === null) {
|
|
226
294
|
return undefined;
|
|
227
295
|
}
|
|
228
296
|
|
|
229
|
-
if (typeof
|
|
230
|
-
const normalized =
|
|
297
|
+
if (typeof inputValue === "string") {
|
|
298
|
+
const normalized = inputValue.trim().toLowerCase();
|
|
231
299
|
if (!normalized) {
|
|
232
300
|
return undefined;
|
|
233
301
|
}
|
|
@@ -243,30 +311,13 @@ const normalizeThemeInput = function(input) {
|
|
|
243
311
|
autoDetectColorScheme: defaultAutoDetectColorSchemeAttrs.slice(),
|
|
244
312
|
};
|
|
245
313
|
}
|
|
246
|
-
const attrs = normalizeAttrList(
|
|
314
|
+
const attrs = normalizeAttrList(inputValue);
|
|
247
315
|
return attrs.length > 0
|
|
248
316
|
? { autoDetectColorScheme: attrs }
|
|
249
317
|
: undefined;
|
|
250
318
|
}
|
|
251
319
|
|
|
252
|
-
|
|
253
|
-
return undefined;
|
|
254
|
-
}
|
|
255
|
-
|
|
256
|
-
const attrs = input
|
|
257
|
-
.filter(function(value) {
|
|
258
|
-
return typeof value === "string";
|
|
259
|
-
})
|
|
260
|
-
.map(function(value) {
|
|
261
|
-
return value.trim();
|
|
262
|
-
})
|
|
263
|
-
.filter(function(value) {
|
|
264
|
-
return value.length > 0;
|
|
265
|
-
});
|
|
266
|
-
|
|
267
|
-
return attrs.length > 0
|
|
268
|
-
? { autoDetectColorScheme: attrs }
|
|
269
|
-
: undefined;
|
|
320
|
+
return undefined;
|
|
270
321
|
};
|
|
271
322
|
|
|
272
323
|
const getThemeInput = function(templateData) {
|
|
@@ -297,6 +348,38 @@ const getConsentState = function() {
|
|
|
297
348
|
return result;
|
|
298
349
|
};
|
|
299
350
|
|
|
351
|
+
const dedupeScopes = function(scopes) {
|
|
352
|
+
const seen = {};
|
|
353
|
+
const result = [];
|
|
354
|
+
for (let index = 0; index < scopes.length; index += 1) {
|
|
355
|
+
const scope = scopes[index];
|
|
356
|
+
if (typeof scope !== "string" || seen[scope]) {
|
|
357
|
+
continue;
|
|
358
|
+
}
|
|
359
|
+
seen[scope] = true;
|
|
360
|
+
result.push(scope);
|
|
361
|
+
}
|
|
362
|
+
return result;
|
|
363
|
+
};
|
|
364
|
+
|
|
365
|
+
const isKnownConsentType = function(consentType) {
|
|
366
|
+
for (let index = 0; index < gtmConsentTypes.length; index += 1) {
|
|
367
|
+
if (gtmConsentTypes[index] === consentType) {
|
|
368
|
+
return true;
|
|
369
|
+
}
|
|
370
|
+
}
|
|
371
|
+
return false;
|
|
372
|
+
};
|
|
373
|
+
|
|
374
|
+
const isHostConfigurableScope = function(scope) {
|
|
375
|
+
for (let index = 0; index < hostConfigurableScopes.length; index += 1) {
|
|
376
|
+
if (hostConfigurableScopes[index] === scope) {
|
|
377
|
+
return true;
|
|
378
|
+
}
|
|
379
|
+
}
|
|
380
|
+
return false;
|
|
381
|
+
};
|
|
382
|
+
|
|
300
383
|
const getManualScopeMappings = function(templateData) {
|
|
301
384
|
const rawRows = Array.isArray(templateData.scopeMappings)
|
|
302
385
|
? templateData.scopeMappings
|
|
@@ -308,74 +391,90 @@ const getManualScopeMappings = function(templateData) {
|
|
|
308
391
|
return undefined;
|
|
309
392
|
}
|
|
310
393
|
const scope = trimString(row.scope);
|
|
311
|
-
const
|
|
312
|
-
if (!scope || !
|
|
394
|
+
const consentType = trimString(row.mapping);
|
|
395
|
+
if (!scope || !consentType) {
|
|
396
|
+
return undefined;
|
|
397
|
+
}
|
|
398
|
+
if (!isHostConfigurableScope(scope) || !isKnownConsentType(consentType)) {
|
|
313
399
|
return undefined;
|
|
314
400
|
}
|
|
315
|
-
return {
|
|
401
|
+
return {
|
|
402
|
+
scope: scope,
|
|
403
|
+
consentType: consentType,
|
|
404
|
+
};
|
|
316
405
|
})
|
|
317
406
|
.filter(function(row) {
|
|
318
|
-
|
|
319
|
-
return false;
|
|
320
|
-
}
|
|
321
|
-
let isHostConfigurableScope = false;
|
|
322
|
-
for (let scopeIndex = 0; scopeIndex < hostConfigurableScopes.length; scopeIndex += 1) {
|
|
323
|
-
if (hostConfigurableScopes[scopeIndex] === row.scope) {
|
|
324
|
-
isHostConfigurableScope = true;
|
|
325
|
-
break;
|
|
326
|
-
}
|
|
327
|
-
}
|
|
328
|
-
if (!isHostConfigurableScope) {
|
|
329
|
-
return false;
|
|
330
|
-
}
|
|
331
|
-
for (let index = 0; index < gtmConsentTypes.length; index += 1) {
|
|
332
|
-
if (gtmConsentTypes[index] === row.consentType) {
|
|
333
|
-
return true;
|
|
334
|
-
}
|
|
335
|
-
}
|
|
336
|
-
return false;
|
|
407
|
+
return row !== undefined;
|
|
337
408
|
});
|
|
338
409
|
};
|
|
339
410
|
|
|
340
|
-
const
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
continue;
|
|
347
|
-
}
|
|
348
|
-
seen[scope] = true;
|
|
349
|
-
result.push(scope);
|
|
411
|
+
const getAnalyticsMeasurementMode = function(templateData) {
|
|
412
|
+
if (
|
|
413
|
+
templateData.analyticsMeasurementMode === "granted" ||
|
|
414
|
+
templateData.analyticsMeasurementMode === "denied"
|
|
415
|
+
) {
|
|
416
|
+
return templateData.analyticsMeasurementMode;
|
|
350
417
|
}
|
|
351
|
-
return
|
|
418
|
+
return "inherit-analytics-storage";
|
|
352
419
|
};
|
|
353
420
|
|
|
354
421
|
const buildDefaultConsent = function(templateData) {
|
|
355
422
|
const consentState = getConsentState();
|
|
356
|
-
const scopeMappings =
|
|
357
|
-
templateData.consentMode === "manual"
|
|
358
|
-
? getManualScopeMappings(templateData)
|
|
359
|
-
: defaultScopeMappings;
|
|
360
423
|
const grantedScopes = [];
|
|
361
424
|
|
|
362
|
-
|
|
363
|
-
const
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
425
|
+
if (templateData.consentMode === "manual") {
|
|
426
|
+
const scopeMappings = getManualScopeMappings(templateData);
|
|
427
|
+
for (let index = 0; index < scopeMappings.length; index += 1) {
|
|
428
|
+
const mapping = scopeMappings[index];
|
|
429
|
+
if (consentState[mapping.consentType] === "granted") {
|
|
430
|
+
grantedScopes.push(mapping.scope);
|
|
431
|
+
}
|
|
432
|
+
}
|
|
433
|
+
} else {
|
|
434
|
+
for (let index = 0; index < defaultScopeMappings.length; index += 1) {
|
|
435
|
+
const mapping = defaultScopeMappings[index];
|
|
436
|
+
if (consentState[mapping.mapping] === "granted") {
|
|
437
|
+
grantedScopes.push(mapping.scope);
|
|
438
|
+
}
|
|
367
439
|
}
|
|
368
|
-
}
|
|
369
440
|
|
|
370
|
-
|
|
371
|
-
|
|
441
|
+
const analyticsMeasurementMode = getAnalyticsMeasurementMode(templateData);
|
|
442
|
+
if (analyticsMeasurementMode === "granted") {
|
|
443
|
+
grantedScopes.push("analytics.measurement");
|
|
444
|
+
}
|
|
445
|
+
if (
|
|
446
|
+
analyticsMeasurementMode === "inherit-analytics-storage" &&
|
|
447
|
+
consentState.analytics_storage === "granted"
|
|
448
|
+
) {
|
|
449
|
+
grantedScopes.push("analytics.measurement");
|
|
450
|
+
}
|
|
372
451
|
}
|
|
373
452
|
|
|
374
453
|
const dedupedScopes = dedupeScopes(grantedScopes);
|
|
375
454
|
return dedupedScopes.length > 0 ? dedupedScopes : undefined;
|
|
376
455
|
};
|
|
377
456
|
|
|
457
|
+
const onSuccess = function() {
|
|
458
|
+
if (typeof data.gtmOnSuccess === "function") {
|
|
459
|
+
data.gtmOnSuccess();
|
|
460
|
+
}
|
|
461
|
+
};
|
|
462
|
+
|
|
463
|
+
const onFailure = function() {
|
|
464
|
+
if (typeof data.gtmOnFailure === "function") {
|
|
465
|
+
data.gtmOnFailure();
|
|
466
|
+
}
|
|
467
|
+
};
|
|
468
|
+
|
|
378
469
|
const apiKey = trimString(data.apiKey);
|
|
470
|
+
if (!apiKey) {
|
|
471
|
+
onFailure();
|
|
472
|
+
return;
|
|
473
|
+
}
|
|
474
|
+
|
|
475
|
+
const widgetUrl =
|
|
476
|
+
loaderScriptBaseUrl + "/" + encodeURIComponent(apiKey) + "/loader.js";
|
|
477
|
+
const queuePush = createQueue(queueKey);
|
|
379
478
|
const initOptions = {
|
|
380
479
|
apiKey: apiKey,
|
|
381
480
|
clientMeta: {
|
|
@@ -394,10 +493,6 @@ if (defaultConsent !== undefined) {
|
|
|
394
493
|
initOptions.defaultConsent = defaultConsent;
|
|
395
494
|
}
|
|
396
495
|
|
|
397
|
-
const widgetUrl =
|
|
398
|
-
loaderScriptBaseUrl + "/" + encodeURIComponent(apiKey) + "/loader.js";
|
|
399
|
-
const queuePush = createQueue("__getuserfeedback_queue");
|
|
400
|
-
|
|
401
496
|
queuePush({
|
|
402
497
|
kind: "init",
|
|
403
498
|
opts: initOptions,
|
|
@@ -405,18 +500,6 @@ queuePush({
|
|
|
405
500
|
|
|
406
501
|
log("Loading getuserfeedback loader:", widgetUrl);
|
|
407
502
|
|
|
408
|
-
const onSuccess = function() {
|
|
409
|
-
if (typeof data.gtmOnSuccess === "function") {
|
|
410
|
-
data.gtmOnSuccess();
|
|
411
|
-
}
|
|
412
|
-
};
|
|
413
|
-
|
|
414
|
-
const onFailure = function() {
|
|
415
|
-
if (typeof data.gtmOnFailure === "function") {
|
|
416
|
-
data.gtmOnFailure();
|
|
417
|
-
}
|
|
418
|
-
};
|
|
419
|
-
|
|
420
503
|
if (queryPermission("inject_script", widgetUrl)) {
|
|
421
504
|
injectScript(widgetUrl, onSuccess, onFailure, "getuserfeedback");
|
|
422
505
|
} else {
|
|
@@ -424,9 +507,65 @@ if (queryPermission("inject_script", widgetUrl)) {
|
|
|
424
507
|
}
|
|
425
508
|
`.trim();
|
|
426
509
|
}
|
|
510
|
+
export function buildGtmPermissions(input) {
|
|
511
|
+
const loaderScriptBaseUrl = trimTrailingSlash(input?.loaderScriptBaseUrl ?? DEFAULT_GTM_LOADER_SCRIPT_BASE_URL);
|
|
512
|
+
const loaderUrlPattern = `${loaderScriptBaseUrl}/*/loader.js`;
|
|
513
|
+
return [
|
|
514
|
+
buildPermission("inject_script", [
|
|
515
|
+
{
|
|
516
|
+
key: "urls",
|
|
517
|
+
value: listValue([stringValue(loaderUrlPattern)]),
|
|
518
|
+
},
|
|
519
|
+
]),
|
|
520
|
+
buildPermission("logging", [
|
|
521
|
+
{
|
|
522
|
+
key: "environments",
|
|
523
|
+
value: stringValue("debug"),
|
|
524
|
+
},
|
|
525
|
+
]),
|
|
526
|
+
buildPermission("access_globals", [
|
|
527
|
+
{
|
|
528
|
+
key: "keys",
|
|
529
|
+
value: listValue([
|
|
530
|
+
mapValue([
|
|
531
|
+
["key", GTM_QUEUE_KEY],
|
|
532
|
+
["read", true],
|
|
533
|
+
["write", true],
|
|
534
|
+
["execute", false],
|
|
535
|
+
]),
|
|
536
|
+
]),
|
|
537
|
+
},
|
|
538
|
+
]),
|
|
539
|
+
buildPermission("access_consent", [
|
|
540
|
+
{
|
|
541
|
+
key: "consentTypes",
|
|
542
|
+
value: listValue(GTM_CONSENT_TYPES.map((consentType) => mapValue([
|
|
543
|
+
["consentType", consentType],
|
|
544
|
+
["read", true],
|
|
545
|
+
["write", false],
|
|
546
|
+
]))),
|
|
547
|
+
},
|
|
548
|
+
]),
|
|
549
|
+
];
|
|
550
|
+
}
|
|
551
|
+
export function buildGtmTemplateInfo(input) {
|
|
552
|
+
return {
|
|
553
|
+
type: "TAG",
|
|
554
|
+
version: GTM_TEMPLATE_VERSION,
|
|
555
|
+
displayName: input?.displayName ?? GTM_TEMPLATE_DEFAULT_DISPLAY_NAME,
|
|
556
|
+
description: input?.description ?? GTM_TEMPLATE_DEFAULT_DESCRIPTION,
|
|
557
|
+
categories: GTM_TEMPLATE_CATEGORIES,
|
|
558
|
+
containerContexts: GTM_TEMPLATE_CONTAINER_CONTEXTS,
|
|
559
|
+
};
|
|
560
|
+
}
|
|
427
561
|
export function buildGtmTemplateParts(input) {
|
|
428
562
|
return {
|
|
429
|
-
|
|
563
|
+
info: buildGtmTemplateInfo(input),
|
|
564
|
+
parameters: buildGtmTemplateParameters(input),
|
|
430
565
|
runtimeSource: buildGtmRuntimeSource(input),
|
|
566
|
+
permissions: buildGtmPermissions(input),
|
|
431
567
|
};
|
|
432
568
|
}
|
|
569
|
+
export function buildGtmTemplateArtifact(input) {
|
|
570
|
+
return buildGtmTemplateParts(input);
|
|
571
|
+
}
|