@miso.ai/client-sdk-ui 1.9.8-beta.2 → 1.9.9-beta.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/dist/cjs/combo/ask/elements.js +1 -0
- package/dist/cjs/combo/ask/index.js +10 -26
- package/dist/cjs/defaults/ask/controls.js +54 -0
- package/dist/cjs/defaults/ask/index.js +17 -0
- package/dist/cjs/layout/radio/feedback.js +30 -29
- package/dist/cjs/version.js +1 -1
- package/dist/cjs/workflow/ask.js +0 -12
- package/package.json +2 -2
- package/src/combo/ask/elements.js +1 -0
- package/src/combo/ask/index.js +6 -19
- package/src/defaults/ask/controls.js +42 -0
- package/src/defaults/ask/index.js +2 -0
- package/src/layout/radio/feedback.js +29 -27
- package/src/version.js +1 -1
- package/src/workflow/ask.js +0 -13
|
@@ -17,6 +17,7 @@ class AskComboElements {
|
|
|
17
17
|
(0, _commons.defineValues)(this, {
|
|
18
18
|
root,
|
|
19
19
|
followUpsSection: root.querySelector(`.${classPrefix}__follow-ups`),
|
|
20
|
+
relatedResourcesSection: root.querySelector(`.${classPrefix}__related-resources`),
|
|
20
21
|
relatedResourcesContainer: root.querySelector(`.${classPrefix}__related-resources miso-ask`)
|
|
21
22
|
});
|
|
22
23
|
}
|
|
@@ -104,10 +104,15 @@ class AskCombo extends _base.default {
|
|
|
104
104
|
}
|
|
105
105
|
async _setupWorkflows() {
|
|
106
106
|
const {
|
|
107
|
+
MisoClient,
|
|
107
108
|
client,
|
|
108
109
|
elements,
|
|
109
110
|
resolvedOptions: options
|
|
110
111
|
} = this;
|
|
112
|
+
const {
|
|
113
|
+
wireFollowUps,
|
|
114
|
+
wireRelatedResources
|
|
115
|
+
} = MisoClient.ui.defaults.ask;
|
|
111
116
|
const {
|
|
112
117
|
templates = {},
|
|
113
118
|
features = {},
|
|
@@ -121,34 +126,13 @@ class AskCombo extends _base.default {
|
|
|
121
126
|
|
|
122
127
|
// TODO: set placeholder if present in options
|
|
123
128
|
|
|
124
|
-
if (
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
let {
|
|
128
|
-
workflow
|
|
129
|
-
} = _ref;
|
|
130
|
-
elements.followUpsSection.insertAdjacentHTML('beforeend', templates.followUp(Object.assign({}, options, {
|
|
131
|
-
parentQuestionId: workflow.questionId
|
|
132
|
-
})));
|
|
133
|
-
});
|
|
134
|
-
// if user starts over, clean up current follow-up questions
|
|
135
|
-
rootWorkflow.on('loading', () => {
|
|
136
|
-
// clean up the entire follow-ups section
|
|
137
|
-
elements.followUpsSection.innerHTML = '';
|
|
138
|
-
// destroy all follow-up workflows
|
|
139
|
-
context.reset({
|
|
140
|
-
root: false
|
|
141
|
-
});
|
|
129
|
+
if (features.followUpQuestions !== false) {
|
|
130
|
+
wireFollowUps(client, elements.followUpsSection, {
|
|
131
|
+
template: templates.followUp
|
|
142
132
|
});
|
|
143
133
|
}
|
|
144
|
-
if (
|
|
145
|
-
|
|
146
|
-
context.on('loading', _ref2 => {
|
|
147
|
-
let {
|
|
148
|
-
workflow
|
|
149
|
-
} = _ref2;
|
|
150
|
-
elements.relatedResourcesContainer.workflow = workflow;
|
|
151
|
-
});
|
|
134
|
+
if (features.relatedResources !== false && features.followUpQuestions !== false) {
|
|
135
|
+
wireRelatedResources(client, elements.relatedResourcesSection);
|
|
152
136
|
}
|
|
153
137
|
|
|
154
138
|
// start query if specified in URL
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports.wireFollowUps = wireFollowUps;
|
|
7
|
+
exports.wireRelatedResources = wireRelatedResources;
|
|
8
|
+
var _templates = require("./templates.js");
|
|
9
|
+
function wireFollowUps(client, element) {
|
|
10
|
+
let {
|
|
11
|
+
template = _templates.followUp
|
|
12
|
+
} = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {};
|
|
13
|
+
if (!client) {
|
|
14
|
+
throw new Error('client is required');
|
|
15
|
+
}
|
|
16
|
+
if (typeof template !== 'function') {
|
|
17
|
+
throw new Error('template must be a function or undefined');
|
|
18
|
+
}
|
|
19
|
+
if (!element) {
|
|
20
|
+
return;
|
|
21
|
+
}
|
|
22
|
+
const context = client.ui.asks;
|
|
23
|
+
const rootWorkflow = client.ui.ask;
|
|
24
|
+
|
|
25
|
+
// 1. when an answer is fully populated, insert a new section for the follow-up question
|
|
26
|
+
context.on('done', event => {
|
|
27
|
+
element.insertAdjacentHTML('beforeend', template({
|
|
28
|
+
parentQuestionId: event.workflow.questionId
|
|
29
|
+
}));
|
|
30
|
+
});
|
|
31
|
+
// 2. if user starts over, clean up existing follow-up questions
|
|
32
|
+
rootWorkflow.on('loading', () => {
|
|
33
|
+
// clean up the entire follow-ups section
|
|
34
|
+
element.innerHTML = '';
|
|
35
|
+
// destroy all follow-up workflows
|
|
36
|
+
context.reset({
|
|
37
|
+
root: false
|
|
38
|
+
});
|
|
39
|
+
});
|
|
40
|
+
}
|
|
41
|
+
function wireRelatedResources(client, element) {
|
|
42
|
+
if (!client) {
|
|
43
|
+
throw new Error('client is required');
|
|
44
|
+
}
|
|
45
|
+
if (!element) {
|
|
46
|
+
return;
|
|
47
|
+
}
|
|
48
|
+
client.ui.asks.on('loading', event => {
|
|
49
|
+
// When a new query starts, associate the last section container (for related resources) to that workflow
|
|
50
|
+
for (const container of element.querySelectorAll('miso-ask')) {
|
|
51
|
+
container.workflow = event.workflow;
|
|
52
|
+
}
|
|
53
|
+
});
|
|
54
|
+
}
|
|
@@ -3,10 +3,27 @@
|
|
|
3
3
|
Object.defineProperty(exports, "__esModule", {
|
|
4
4
|
value: true
|
|
5
5
|
});
|
|
6
|
+
var _exportNames = {
|
|
7
|
+
constants: true,
|
|
8
|
+
phrases: true,
|
|
9
|
+
templates: true
|
|
10
|
+
};
|
|
6
11
|
exports.templates = exports.phrases = exports.constants = void 0;
|
|
7
12
|
var _constants = _interopRequireWildcard(require("./constants.js"));
|
|
8
13
|
var _phrases = _interopRequireWildcard(require("./phrases.js"));
|
|
9
14
|
var _templates = _interopRequireWildcard(require("./templates.js"));
|
|
15
|
+
var _controls = require("./controls.js");
|
|
16
|
+
Object.keys(_controls).forEach(function (key) {
|
|
17
|
+
if (key === "default" || key === "__esModule") return;
|
|
18
|
+
if (Object.prototype.hasOwnProperty.call(_exportNames, key)) return;
|
|
19
|
+
if (key in exports && exports[key] === _controls[key]) return;
|
|
20
|
+
Object.defineProperty(exports, key, {
|
|
21
|
+
enumerable: true,
|
|
22
|
+
get: function () {
|
|
23
|
+
return _controls[key];
|
|
24
|
+
}
|
|
25
|
+
});
|
|
26
|
+
});
|
|
10
27
|
function _getRequireWildcardCache(e) { if ("function" != typeof WeakMap) return null; var r = new WeakMap(), t = new WeakMap(); return (_getRequireWildcardCache = function (e) { return e ? t : r; })(e); }
|
|
11
28
|
function _interopRequireWildcard(e, r) { if (!r && e && e.__esModule) return e; if (null === e || "object" != typeof e && "function" != typeof e) return { default: e }; var t = _getRequireWildcardCache(r); if (t && t.has(e)) return t.get(e); var n = { __proto__: null }, a = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var u in e) if ("default" !== u && {}.hasOwnProperty.call(e, u)) { var i = a ? Object.getOwnPropertyDescriptor(e, u) : null; i && (i.get || i.set) ? Object.defineProperty(n, u, i) : n[u] = e[u]; } return n.default = e, t && t.set(e, n), n; }
|
|
12
29
|
const constants = exports.constants = Object.freeze(_constants);
|
|
@@ -12,52 +12,53 @@ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { de
|
|
|
12
12
|
function _objectWithoutPropertiesLoose(source, excluded) { if (source == null) return {}; var target = {}; var sourceKeys = Object.keys(source); var key, i; for (i = 0; i < sourceKeys.length; i++) { key = sourceKeys[i]; if (excluded.indexOf(key) >= 0) continue; target[key] = source[key]; } return target; }
|
|
13
13
|
const TYPE = 'feedback';
|
|
14
14
|
const DEFAULT_CLASSNAME = 'miso-feedback';
|
|
15
|
-
|
|
16
|
-
const {
|
|
17
|
-
className,
|
|
18
|
-
role,
|
|
19
|
-
templates,
|
|
20
|
-
options
|
|
21
|
-
} = layout;
|
|
22
|
-
const roleAttr = role ? `data-role="${role}"` : '';
|
|
23
|
-
return `
|
|
24
|
-
<div class="${className}" ${roleAttr}>
|
|
25
|
-
${options.options.map(option => templates.option(layout, option))}
|
|
26
|
-
</div>
|
|
27
|
-
`;
|
|
28
|
-
}
|
|
29
|
-
const OPTIONS = [{
|
|
30
|
-
text: 'Helpful',
|
|
31
|
-
value: 'helpful',
|
|
32
|
-
icon: _svgs.THUMB
|
|
33
|
-
}, {
|
|
34
|
-
text: 'Not helpful',
|
|
35
|
-
value: 'unhelpful',
|
|
36
|
-
icon: _svgs.THUMB
|
|
37
|
-
}];
|
|
15
|
+
const OPTIONS = ['helpful', 'unhelpful'];
|
|
38
16
|
function options(layout) {
|
|
39
17
|
const {
|
|
40
18
|
templates
|
|
41
19
|
} = layout;
|
|
42
|
-
return OPTIONS.map(
|
|
20
|
+
return OPTIONS.map(value => templates.option(layout, {
|
|
21
|
+
value
|
|
22
|
+
})).join('');
|
|
43
23
|
}
|
|
44
24
|
function content(layout, _ref) {
|
|
45
25
|
let {
|
|
46
|
-
|
|
47
|
-
icon
|
|
26
|
+
value
|
|
48
27
|
} = _ref;
|
|
49
28
|
const {
|
|
50
29
|
className,
|
|
30
|
+
templates,
|
|
51
31
|
options = {}
|
|
52
32
|
} = layout;
|
|
53
33
|
return `
|
|
54
|
-
${options.icon !== false ? `<i class="${className}__icon">${icon}</i>` : ''}
|
|
55
|
-
${options.text !== false ? `<span class="${className}__text">${text}</span>` : ''}
|
|
34
|
+
${options.icon !== false ? `<i class="${className}__icon">${templates.icon(layout, value)}</i>` : ''}
|
|
35
|
+
${options.text !== false ? `<span class="${className}__text">${templates.text(layout, value)}</span>` : ''}
|
|
56
36
|
`;
|
|
57
37
|
}
|
|
38
|
+
function icon(layout, value) {
|
|
39
|
+
switch (value) {
|
|
40
|
+
case 'helpful':
|
|
41
|
+
case 'unhelpful':
|
|
42
|
+
return _svgs.THUMB;
|
|
43
|
+
default:
|
|
44
|
+
return '';
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
function text(layout, value) {
|
|
48
|
+
switch (value) {
|
|
49
|
+
case 'helpful':
|
|
50
|
+
return 'Helpful';
|
|
51
|
+
case 'unhelpful':
|
|
52
|
+
return 'Not helpful';
|
|
53
|
+
default:
|
|
54
|
+
return '';
|
|
55
|
+
}
|
|
56
|
+
}
|
|
58
57
|
const DEFAULT_TEMPLATES = Object.freeze({
|
|
59
58
|
options,
|
|
60
|
-
content
|
|
59
|
+
content,
|
|
60
|
+
icon,
|
|
61
|
+
text
|
|
61
62
|
});
|
|
62
63
|
class FeedbackLayout extends _radio.default {
|
|
63
64
|
static get category() {
|
package/dist/cjs/version.js
CHANGED
package/dist/cjs/workflow/ask.js
CHANGED
|
@@ -229,18 +229,6 @@ class Ask extends _base.default {
|
|
|
229
229
|
})
|
|
230
230
|
});
|
|
231
231
|
}
|
|
232
|
-
_onDataUpdate(data) {
|
|
233
|
-
// TODO: can we just put this in _defaultProcessData?
|
|
234
|
-
if (this._questionId) {
|
|
235
|
-
return;
|
|
236
|
-
}
|
|
237
|
-
const questionId = data && data.value && data.value.question_id;
|
|
238
|
-
// capture question ID and register at context
|
|
239
|
-
if (questionId) {
|
|
240
|
-
this._questionId = questionId;
|
|
241
|
-
this._context._byQid.set(questionId, this);
|
|
242
|
-
}
|
|
243
|
-
}
|
|
244
232
|
_onAnswerViewUpdate(_ref2) {
|
|
245
233
|
let {
|
|
246
234
|
session,
|
package/package.json
CHANGED
|
@@ -10,6 +10,7 @@ export default class AskComboElements {
|
|
|
10
10
|
defineValues(this, {
|
|
11
11
|
root,
|
|
12
12
|
followUpsSection: root.querySelector(`.${classPrefix}__follow-ups`),
|
|
13
|
+
relatedResourcesSection: root.querySelector(`.${classPrefix}__related-resources`),
|
|
13
14
|
relatedResourcesContainer: root.querySelector(`.${classPrefix}__related-resources miso-ask`),
|
|
14
15
|
});
|
|
15
16
|
}
|
package/src/combo/ask/index.js
CHANGED
|
@@ -98,7 +98,8 @@ export default class AskCombo extends Combo {
|
|
|
98
98
|
}
|
|
99
99
|
|
|
100
100
|
async _setupWorkflows() {
|
|
101
|
-
const { client, elements, resolvedOptions: options } = this;
|
|
101
|
+
const { MisoClient, client, elements, resolvedOptions: options } = this;
|
|
102
|
+
const { wireFollowUps, wireRelatedResources } = MisoClient.ui.defaults.ask;
|
|
102
103
|
const { templates = {}, features = {}, api } = options;
|
|
103
104
|
|
|
104
105
|
const context = client.ui.asks;
|
|
@@ -110,25 +111,11 @@ export default class AskCombo extends Combo {
|
|
|
110
111
|
|
|
111
112
|
// TODO: set placeholder if present in options
|
|
112
113
|
|
|
113
|
-
if (
|
|
114
|
-
|
|
115
|
-
context.on('done', ({ workflow }) => {
|
|
116
|
-
elements.followUpsSection.insertAdjacentHTML('beforeend', templates.followUp({ ...options, parentQuestionId: workflow.questionId }));
|
|
117
|
-
});
|
|
118
|
-
// if user starts over, clean up current follow-up questions
|
|
119
|
-
rootWorkflow.on('loading', () => {
|
|
120
|
-
// clean up the entire follow-ups section
|
|
121
|
-
elements.followUpsSection.innerHTML = '';
|
|
122
|
-
// destroy all follow-up workflows
|
|
123
|
-
context.reset({ root: false });
|
|
124
|
-
});
|
|
114
|
+
if (features.followUpQuestions !== false) {
|
|
115
|
+
wireFollowUps(client, elements.followUpsSection, { template: templates.followUp });
|
|
125
116
|
}
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
// when a new query starts, associate the last section container (for related resources) to that workflow
|
|
129
|
-
context.on('loading', ({ workflow }) => {
|
|
130
|
-
elements.relatedResourcesContainer.workflow = workflow;
|
|
131
|
-
});
|
|
117
|
+
if (features.relatedResources !== false && features.followUpQuestions !== false) {
|
|
118
|
+
wireRelatedResources(client, elements.relatedResourcesSection);
|
|
132
119
|
}
|
|
133
120
|
|
|
134
121
|
// start query if specified in URL
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import { followUp as followUpTemplate } from './templates.js';
|
|
2
|
+
|
|
3
|
+
export function wireFollowUps(client, element, { template = followUpTemplate } = {}) {
|
|
4
|
+
if (!client) {
|
|
5
|
+
throw new Error('client is required');
|
|
6
|
+
}
|
|
7
|
+
if (typeof template !== 'function') {
|
|
8
|
+
throw new Error('template must be a function or undefined');
|
|
9
|
+
}
|
|
10
|
+
if (!element) {
|
|
11
|
+
return;
|
|
12
|
+
}
|
|
13
|
+
const context = client.ui.asks;
|
|
14
|
+
const rootWorkflow = client.ui.ask;
|
|
15
|
+
|
|
16
|
+
// 1. when an answer is fully populated, insert a new section for the follow-up question
|
|
17
|
+
context.on('done', (event) => {
|
|
18
|
+
element.insertAdjacentHTML('beforeend', template({ parentQuestionId: event.workflow.questionId }));
|
|
19
|
+
});
|
|
20
|
+
// 2. if user starts over, clean up existing follow-up questions
|
|
21
|
+
rootWorkflow.on('loading', () => {
|
|
22
|
+
// clean up the entire follow-ups section
|
|
23
|
+
element.innerHTML = '';
|
|
24
|
+
// destroy all follow-up workflows
|
|
25
|
+
context.reset({ root: false });
|
|
26
|
+
});
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
export function wireRelatedResources(client, element) {
|
|
30
|
+
if (!client) {
|
|
31
|
+
throw new Error('client is required');
|
|
32
|
+
}
|
|
33
|
+
if (!element) {
|
|
34
|
+
return;
|
|
35
|
+
}
|
|
36
|
+
client.ui.asks.on('loading', (event) => {
|
|
37
|
+
// When a new query starts, associate the last section container (for related resources) to that workflow
|
|
38
|
+
for (const container of element.querySelectorAll('miso-ask')) {
|
|
39
|
+
container.workflow = event.workflow;
|
|
40
|
+
}
|
|
41
|
+
});
|
|
42
|
+
}
|
|
@@ -2,6 +2,8 @@ import * as _constants from './constants.js';
|
|
|
2
2
|
import * as _phrases from './phrases.js';
|
|
3
3
|
import * as _templates from './templates.js';
|
|
4
4
|
|
|
5
|
+
export * from './controls.js';
|
|
6
|
+
|
|
5
7
|
export const constants = Object.freeze(_constants);
|
|
6
8
|
export const phrases = Object.freeze(_phrases);
|
|
7
9
|
export const templates = Object.freeze(_templates);
|
|
@@ -5,45 +5,47 @@ import { THUMB } from '../svgs.js';
|
|
|
5
5
|
const TYPE = 'feedback';
|
|
6
6
|
const DEFAULT_CLASSNAME = 'miso-feedback';
|
|
7
7
|
|
|
8
|
-
|
|
9
|
-
const { className, role, templates, options } = layout;
|
|
10
|
-
const roleAttr = role ? `data-role="${role}"` : '';
|
|
11
|
-
return `
|
|
12
|
-
<div class="${className}" ${roleAttr}>
|
|
13
|
-
${options.options.map((option) => templates.option(layout, option))}
|
|
14
|
-
</div>
|
|
15
|
-
`;
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
const OPTIONS = [
|
|
19
|
-
{
|
|
20
|
-
text: 'Helpful',
|
|
21
|
-
value: 'helpful',
|
|
22
|
-
icon: THUMB,
|
|
23
|
-
},
|
|
24
|
-
{
|
|
25
|
-
text: 'Not helpful',
|
|
26
|
-
value: 'unhelpful',
|
|
27
|
-
icon: THUMB,
|
|
28
|
-
},
|
|
29
|
-
];
|
|
8
|
+
const OPTIONS = [ 'helpful', 'unhelpful' ];
|
|
30
9
|
|
|
31
10
|
function options(layout) {
|
|
32
11
|
const { templates } = layout;
|
|
33
|
-
return OPTIONS.map(
|
|
12
|
+
return OPTIONS.map(value => templates.option(layout, { value })).join('');
|
|
34
13
|
}
|
|
35
14
|
|
|
36
|
-
function content(layout, {
|
|
37
|
-
const { className, options = {} } = layout;
|
|
15
|
+
function content(layout, { value }) {
|
|
16
|
+
const { className, templates, options = {} } = layout;
|
|
38
17
|
return `
|
|
39
|
-
${options.icon !== false ? `<i class="${className}__icon">${icon}</i>` : ''}
|
|
40
|
-
${options.text !== false ? `<span class="${className}__text">${text}</span>` : ''}
|
|
18
|
+
${options.icon !== false ? `<i class="${className}__icon">${templates.icon(layout, value)}</i>` : ''}
|
|
19
|
+
${options.text !== false ? `<span class="${className}__text">${templates.text(layout, value)}</span>` : ''}
|
|
41
20
|
`;
|
|
42
21
|
}
|
|
43
22
|
|
|
23
|
+
function icon(layout, value) {
|
|
24
|
+
switch (value) {
|
|
25
|
+
case 'helpful':
|
|
26
|
+
case 'unhelpful':
|
|
27
|
+
return THUMB;
|
|
28
|
+
default:
|
|
29
|
+
return '';
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
function text(layout, value) {
|
|
34
|
+
switch (value) {
|
|
35
|
+
case 'helpful':
|
|
36
|
+
return 'Helpful';
|
|
37
|
+
case 'unhelpful':
|
|
38
|
+
return 'Not helpful';
|
|
39
|
+
default:
|
|
40
|
+
return '';
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
|
|
44
44
|
const DEFAULT_TEMPLATES = Object.freeze({
|
|
45
45
|
options,
|
|
46
46
|
content,
|
|
47
|
+
icon,
|
|
48
|
+
text,
|
|
47
49
|
});
|
|
48
50
|
|
|
49
51
|
export default class FeedbackLayout extends RadioLayout {
|
package/src/version.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export default '1.9.
|
|
1
|
+
export default '1.9.9-beta.0';
|
package/src/workflow/ask.js
CHANGED
|
@@ -190,19 +190,6 @@ export default class Ask extends Workflow {
|
|
|
190
190
|
};
|
|
191
191
|
}
|
|
192
192
|
|
|
193
|
-
_onDataUpdate(data) {
|
|
194
|
-
// TODO: can we just put this in _defaultProcessData?
|
|
195
|
-
if (this._questionId) {
|
|
196
|
-
return;
|
|
197
|
-
}
|
|
198
|
-
const questionId = data && data.value && data.value.question_id;
|
|
199
|
-
// capture question ID and register at context
|
|
200
|
-
if (questionId) {
|
|
201
|
-
this._questionId = questionId;
|
|
202
|
-
this._context._byQid.set(questionId, this);
|
|
203
|
-
}
|
|
204
|
-
}
|
|
205
|
-
|
|
206
193
|
_onAnswerViewUpdate({ session, status, ongoing }) {
|
|
207
194
|
if (status === STATUS.INITIAL) {
|
|
208
195
|
return;
|