@memberjunction/server 0.9.157 → 0.9.159
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/build.log.json
CHANGED
|
@@ -22,7 +22,11 @@ const core_1 = require("@memberjunction/core");
|
|
|
22
22
|
const sqlserver_dataprovider_1 = require("@memberjunction/sqlserver-dataprovider");
|
|
23
23
|
const skip_types_1 = require("@memberjunction/skip-types");
|
|
24
24
|
const axios_1 = __importDefault(require("axios"));
|
|
25
|
+
const zlib_1 = __importDefault(require("zlib"));
|
|
26
|
+
const util_1 = require("util");
|
|
27
|
+
const gzip = (0, util_1.promisify)(zlib_1.default.gzip);
|
|
25
28
|
const PushStatusResolver_1 = require("../generic/PushStatusResolver");
|
|
29
|
+
const ___skipAPIurl = 'http://localhost:8000';
|
|
26
30
|
let AskSkipResultType = class AskSkipResultType {
|
|
27
31
|
};
|
|
28
32
|
exports.AskSkipResultType = AskSkipResultType;
|
|
@@ -88,10 +92,7 @@ let AskSkipResolver = AskSkipResolver_1 = class AskSkipResolver {
|
|
|
88
92
|
dataContext.Items.push({
|
|
89
93
|
Type: 'view',
|
|
90
94
|
RecordID: ViewId,
|
|
91
|
-
|
|
92
|
-
dataContext.Items.push({
|
|
93
|
-
Type: 'view',
|
|
94
|
-
RecordID: 123,
|
|
95
|
+
Data: await this.getViewData(ViewId, user),
|
|
95
96
|
});
|
|
96
97
|
const messages = [
|
|
97
98
|
{
|
|
@@ -106,19 +107,23 @@ let AskSkipResolver = AskSkipResolver_1 = class AskSkipResolver {
|
|
|
106
107
|
organizationID: !isNaN(parseInt(OrganizationId)) ? parseInt(OrganizationId) : 0,
|
|
107
108
|
requestPhase: 'initial_request'
|
|
108
109
|
};
|
|
109
|
-
const url = 'http://localhost:8000';
|
|
110
110
|
pubSub.publish(PushStatusResolver_1.PUSH_STATUS_UPDATES_TOPIC, {
|
|
111
111
|
message: JSON.stringify({
|
|
112
112
|
type: 'AskSkip',
|
|
113
113
|
status: 'OK',
|
|
114
|
-
message: '
|
|
114
|
+
message: 'I will be happy to help and will start by analyzing your request...',
|
|
115
115
|
}),
|
|
116
116
|
sessionId: userPayload.sessionId,
|
|
117
117
|
});
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
118
|
+
return this.HandleSkipRequest(input, UserQuestion, user, dataSource, ConversationId, userPayload, pubSub, md, convoEntity, convoDetailEntity);
|
|
119
|
+
}
|
|
120
|
+
async HandleSkipRequest(input, UserQuestion, user, dataSource, ConversationId, userPayload, pubSub, md, convoEntity, convoDetailEntity) {
|
|
121
|
+
const compressedPayload = await gzip(Buffer.from(JSON.stringify(input)));
|
|
122
|
+
const response = await axios_1.default.post(___skipAPIurl, compressedPayload, {
|
|
123
|
+
headers: {
|
|
124
|
+
'Content-Type': 'application/json',
|
|
125
|
+
'Content-Encoding': 'gzip'
|
|
126
|
+
}
|
|
122
127
|
});
|
|
123
128
|
if (response.status === 200) {
|
|
124
129
|
const apiResponse = response.data;
|
|
@@ -142,24 +147,23 @@ let AskSkipResolver = AskSkipResolver_1 = class AskSkipResolver {
|
|
|
142
147
|
}),
|
|
143
148
|
sessionId: userPayload.sessionId,
|
|
144
149
|
});
|
|
145
|
-
let nextAPIResponse = null;
|
|
146
150
|
if (apiResponse.responsePhase === 'data_request') {
|
|
147
|
-
|
|
151
|
+
return await this.HandleDataRequestPhase(input, apiResponse, UserQuestion, user, dataSource, ConversationId, userPayload, pubSub);
|
|
148
152
|
}
|
|
149
153
|
else if (apiResponse.responsePhase === 'clarifying_question') {
|
|
154
|
+
throw new Error('Clarifying question not implemented yet');
|
|
150
155
|
}
|
|
151
|
-
else
|
|
152
|
-
|
|
156
|
+
else {
|
|
157
|
+
const { AIMessageConversationDetailID } = await this.FinishConversationAndNotifyUser(apiResponse, md, user, convoEntity, pubSub, userPayload);
|
|
158
|
+
return {
|
|
159
|
+
Success: true,
|
|
160
|
+
Status: 'OK',
|
|
161
|
+
ConversationId: ConversationId,
|
|
162
|
+
UserMessageConversationDetailId: convoDetailEntity.ID,
|
|
163
|
+
AIMessageConversationDetailId: AIMessageConversationDetailID,
|
|
164
|
+
Result: JSON.stringify(response.data)
|
|
165
|
+
};
|
|
153
166
|
}
|
|
154
|
-
const { AIMessageConversationDetailID } = await this.FinishConversationAndNotifyUser(apiResponse, md, user, convoEntity, pubSub, userPayload);
|
|
155
|
-
return {
|
|
156
|
-
Success: true,
|
|
157
|
-
Status: 'OK',
|
|
158
|
-
ConversationId: ConversationId,
|
|
159
|
-
UserMessageConversationDetailId: convoDetailEntity.ID,
|
|
160
|
-
AIMessageConversationDetailId: AIMessageConversationDetailID,
|
|
161
|
-
Result: JSON.stringify(response.data)
|
|
162
|
-
};
|
|
163
167
|
}
|
|
164
168
|
else {
|
|
165
169
|
pubSub.publish(PushStatusResolver_1.PUSH_STATUS_UPDATES_TOPIC, {
|
|
@@ -180,8 +184,61 @@ let AskSkipResolver = AskSkipResolver_1 = class AskSkipResolver {
|
|
|
180
184
|
};
|
|
181
185
|
}
|
|
182
186
|
}
|
|
183
|
-
async HandleDataRequestPhase(apiResponse, user, dataSource, ConversationId, userPayload, pubSub) {
|
|
184
|
-
|
|
187
|
+
async HandleDataRequestPhase(apiRequest, apiResponse, UserQuestion, user, dataSource, ConversationId, userPayload, pubSub) {
|
|
188
|
+
try {
|
|
189
|
+
pubSub.publish(PushStatusResolver_1.PUSH_STATUS_UPDATES_TOPIC, {
|
|
190
|
+
message: JSON.stringify({
|
|
191
|
+
type: 'AskSkip',
|
|
192
|
+
status: 'OK',
|
|
193
|
+
message: 'I am gathering some data needed for your request, once that\'s done I\'ll analyze it for you...',
|
|
194
|
+
}),
|
|
195
|
+
sessionId: userPayload.sessionId,
|
|
196
|
+
});
|
|
197
|
+
const md = new core_1.Metadata();
|
|
198
|
+
for (const dr of apiResponse.dataRequest) {
|
|
199
|
+
switch (dr.type) {
|
|
200
|
+
case "sql":
|
|
201
|
+
const sql = dr.text;
|
|
202
|
+
const result = await dataSource.query(sql);
|
|
203
|
+
if (!result)
|
|
204
|
+
throw new Error(`Error running SQL: ${sql}`);
|
|
205
|
+
const item = new skip_types_1.SkipDataContextItem();
|
|
206
|
+
item.Type = 'sql';
|
|
207
|
+
item.Data = result;
|
|
208
|
+
item.RecordName = dr.text;
|
|
209
|
+
item.AdditionalDescription = dr.description;
|
|
210
|
+
apiRequest.dataContext.Items.push(item);
|
|
211
|
+
break;
|
|
212
|
+
case "stored_query":
|
|
213
|
+
const queryName = dr.text;
|
|
214
|
+
const query = md.Queries.find((q) => q.Name === queryName);
|
|
215
|
+
if (query) {
|
|
216
|
+
const rq = new core_1.RunQuery();
|
|
217
|
+
const result = await rq.RunQuery({ QueryID: query.ID }, user);
|
|
218
|
+
if (result && result.Success) {
|
|
219
|
+
const item = new skip_types_1.SkipDataContextItem();
|
|
220
|
+
item.Type = 'query';
|
|
221
|
+
item.Data = result.Results;
|
|
222
|
+
item.RecordID = query.ID;
|
|
223
|
+
item.RecordName = query.Name;
|
|
224
|
+
item.AdditionalDescription = dr.description;
|
|
225
|
+
apiRequest.dataContext.Items.push(item);
|
|
226
|
+
}
|
|
227
|
+
else
|
|
228
|
+
throw new Error(`Error running query ${queryName}`);
|
|
229
|
+
}
|
|
230
|
+
else
|
|
231
|
+
throw new Error(`Query ${queryName} not found.`);
|
|
232
|
+
break;
|
|
233
|
+
}
|
|
234
|
+
}
|
|
235
|
+
apiRequest.requestPhase = 'data_gathering_response';
|
|
236
|
+
return this.HandleSkipRequest(apiRequest, UserQuestion, user, dataSource, ConversationId, userPayload, pubSub, md, null, null);
|
|
237
|
+
}
|
|
238
|
+
catch (e) {
|
|
239
|
+
(0, core_1.LogError)(e);
|
|
240
|
+
throw e;
|
|
241
|
+
}
|
|
185
242
|
}
|
|
186
243
|
async FinishConversationAndNotifyUser(apiResponse, md, user, convoEntity, pubSub, userPayload) {
|
|
187
244
|
const sTitle = apiResponse.reportTitle;
|
|
@@ -223,6 +280,14 @@ let AskSkipResolver = AskSkipResolver_1 = class AskSkipResolver {
|
|
|
223
280
|
AIMessageConversationDetailID: convoDetailEntityAI.ID
|
|
224
281
|
};
|
|
225
282
|
}
|
|
283
|
+
async getViewData(ViewId, user) {
|
|
284
|
+
const rv = new core_1.RunView();
|
|
285
|
+
const result = await rv.RunView({ ViewID: ViewId, IgnoreMaxRows: true }, user);
|
|
286
|
+
if (result && result.Success)
|
|
287
|
+
return result.Results;
|
|
288
|
+
else
|
|
289
|
+
throw new Error(`Error running view ${ViewId}`);
|
|
290
|
+
}
|
|
226
291
|
};
|
|
227
292
|
exports.AskSkipResolver = AskSkipResolver;
|
|
228
293
|
AskSkipResolver._defaultNewChatName = 'New Chat';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"AskSkipResolver.js","sourceRoot":"","sources":["../../src/resolvers/AskSkipResolver.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;AAAA,+CAAuG;AACvG,+
|
|
1
|
+
{"version":3,"file":"AskSkipResolver.js","sourceRoot":"","sources":["../../src/resolvers/AskSkipResolver.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@memberjunction/server",
|
|
3
|
-
"version": "0.9.
|
|
3
|
+
"version": "0.9.159",
|
|
4
4
|
"description": "MemberJunction: This project provides API access via GraphQL to the common data store.",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"types": "src/index.ts",
|
|
@@ -28,7 +28,7 @@
|
|
|
28
28
|
"@memberjunction/global": "^0.9.132",
|
|
29
29
|
"@memberjunction/queue": "^0.9.139",
|
|
30
30
|
"@memberjunction/sqlserver-dataprovider": "^0.9.150",
|
|
31
|
-
"@memberjunction/skip-types": "^0.9.
|
|
31
|
+
"@memberjunction/skip-types": "^0.9.10",
|
|
32
32
|
"@types/cors": "^2.8.13",
|
|
33
33
|
"@types/jsonwebtoken": "^8.5.9",
|
|
34
34
|
"@types/node": "^18.11.14",
|
|
@@ -1,14 +1,25 @@
|
|
|
1
1
|
import { Arg, Ctx, Field, Int, ObjectType, PubSub, PubSubEngine, Query, Resolver } from 'type-graphql';
|
|
2
|
-
import { Metadata, UserInfo } from '@memberjunction/core';
|
|
2
|
+
import { LogError, Metadata, RunQuery, RunQueryParams, RunView, UserInfo } from '@memberjunction/core';
|
|
3
3
|
import { AppContext, UserPayload } from '../types';
|
|
4
4
|
import { UserCache } from '@memberjunction/sqlserver-dataprovider';
|
|
5
|
-
import { SkipDataContext, SkipDataContextItem, SkipAPIRequest, SkipAPIResponse, SkipMessage, SkipAPIAnalysisCompleteResponse } from '@memberjunction/skip-types';
|
|
5
|
+
import { SkipDataContext, SkipDataContextItem, SkipAPIRequest, SkipAPIResponse, SkipMessage, SkipAPIAnalysisCompleteResponse, SkipAPIDataRequestResponse } from '@memberjunction/skip-types';
|
|
6
6
|
import axios from 'axios';
|
|
7
|
+
import zlib from 'zlib';
|
|
8
|
+
import { promisify } from 'util';
|
|
9
|
+
// Convert zlib.gzip into a promise-returning function
|
|
10
|
+
const gzip = promisify(zlib.gzip);
|
|
7
11
|
|
|
8
12
|
import { PUSH_STATUS_UPDATES_TOPIC } from '../generic/PushStatusResolver';
|
|
9
13
|
import { ConversationDetailEntity, ConversationEntity, UserNotificationEntity, UserViewEntityExtended } from '@memberjunction/core-entities';
|
|
10
14
|
import { DataSource } from 'typeorm';
|
|
11
15
|
|
|
16
|
+
|
|
17
|
+
const ___skipAPIurl = 'http://localhost:8000'
|
|
18
|
+
// const url = process.env.BOT_EXTERNAL_API_URL;
|
|
19
|
+
// TEMP - call the separate server, we'll move this to real skip server soon!!!!!
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
|
|
12
23
|
@ObjectType()
|
|
13
24
|
export class AskSkipResultType {
|
|
14
25
|
@Field(() => Boolean)
|
|
@@ -78,14 +89,9 @@ export class AskSkipResolver {
|
|
|
78
89
|
{
|
|
79
90
|
Type: 'view',
|
|
80
91
|
RecordID: ViewId,
|
|
92
|
+
Data: await this.getViewData(ViewId, user),
|
|
81
93
|
} as SkipDataContextItem
|
|
82
94
|
);
|
|
83
|
-
dataContext.Items.push(
|
|
84
|
-
{
|
|
85
|
-
Type: 'view',
|
|
86
|
-
RecordID: 123, //test adding an extra item to the data context
|
|
87
|
-
} as SkipDataContextItem
|
|
88
|
-
);
|
|
89
95
|
|
|
90
96
|
const messages: SkipMessage[] = [
|
|
91
97
|
{
|
|
@@ -102,26 +108,39 @@ export class AskSkipResolver {
|
|
|
102
108
|
requestPhase: 'initial_request'
|
|
103
109
|
};
|
|
104
110
|
|
|
105
|
-
const url = 'http://localhost:8000'
|
|
106
|
-
// const url = process.env.BOT_EXTERNAL_API_URL;
|
|
107
|
-
// TEMP - call the separate server, we'll move this to real skip server soon!!!!!
|
|
108
|
-
|
|
109
|
-
|
|
110
111
|
pubSub.publish(PUSH_STATUS_UPDATES_TOPIC, {
|
|
111
112
|
message: JSON.stringify({
|
|
112
113
|
type: 'AskSkip',
|
|
113
114
|
status: 'OK',
|
|
114
|
-
message: '
|
|
115
|
+
message: 'I will be happy to help and will start by analyzing your request...',
|
|
115
116
|
}),
|
|
116
117
|
sessionId: userPayload.sessionId,
|
|
117
118
|
});
|
|
118
119
|
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
120
|
+
return this.HandleSkipRequest(input, UserQuestion, user, dataSource, ConversationId, userPayload, pubSub, md, convoEntity, convoDetailEntity);
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
|
|
124
|
+
protected async HandleSkipRequest(input: SkipAPIRequest, UserQuestion: string, user: UserInfo, dataSource: DataSource,
|
|
125
|
+
ConversationId: number, userPayload: UserPayload, pubSub: PubSubEngine, md: Metadata,
|
|
126
|
+
convoEntity: ConversationEntity, convoDetailEntity: ConversationDetailEntity): Promise<AskSkipResultType> {
|
|
127
|
+
// Convert JSON payload to a Buffer and compress it
|
|
128
|
+
const compressedPayload = await gzip(Buffer.from(JSON.stringify(input)));
|
|
129
|
+
|
|
130
|
+
// Send the compressed payload with Axios
|
|
131
|
+
const response = await axios.post(___skipAPIurl, compressedPayload, {
|
|
132
|
+
headers: {
|
|
133
|
+
'Content-Type': 'application/json',
|
|
134
|
+
'Content-Encoding': 'gzip'
|
|
135
|
+
}
|
|
123
136
|
});
|
|
124
137
|
|
|
138
|
+
// const response = await axios({
|
|
139
|
+
// method: 'post',
|
|
140
|
+
// url: ___skipAPIurl,
|
|
141
|
+
// data: input,
|
|
142
|
+
// });
|
|
143
|
+
|
|
125
144
|
if (response.status === 200) {
|
|
126
145
|
const apiResponse = <SkipAPIResponse>response.data;
|
|
127
146
|
let sUserMessage: string = '';
|
|
@@ -148,28 +167,28 @@ export class AskSkipResolver {
|
|
|
148
167
|
});
|
|
149
168
|
|
|
150
169
|
// now, based on the result type, we will either wait for the next phase or we will process the results
|
|
151
|
-
let nextAPIResponse: SkipAPIResponse | null = null;
|
|
152
170
|
if (apiResponse.responsePhase === 'data_request') {
|
|
153
|
-
|
|
171
|
+
return await this.HandleDataRequestPhase(input, <SkipAPIDataRequestResponse>apiResponse, UserQuestion, user, dataSource, ConversationId, userPayload, pubSub);
|
|
154
172
|
}
|
|
155
173
|
else if (apiResponse.responsePhase === 'clarifying_question') {
|
|
156
174
|
// need to send the request back to the user for a clarifying question
|
|
157
175
|
// TO-DO implement this
|
|
176
|
+
throw new Error('Clarifying question not implemented yet');
|
|
158
177
|
}
|
|
159
|
-
else
|
|
160
|
-
|
|
178
|
+
else { // apiResponse.responsePhase === 'analysis_complete'
|
|
179
|
+
// analysis is complete
|
|
180
|
+
// all done, wrap things up
|
|
181
|
+
const {AIMessageConversationDetailID} = await this.FinishConversationAndNotifyUser(apiResponse, md, user, convoEntity, pubSub, userPayload);
|
|
182
|
+
|
|
183
|
+
return {
|
|
184
|
+
Success: true,
|
|
185
|
+
Status: 'OK',
|
|
186
|
+
ConversationId: ConversationId,
|
|
187
|
+
UserMessageConversationDetailId: convoDetailEntity.ID,
|
|
188
|
+
AIMessageConversationDetailId: AIMessageConversationDetailID,
|
|
189
|
+
Result: JSON.stringify(response.data)
|
|
190
|
+
};
|
|
161
191
|
}
|
|
162
|
-
|
|
163
|
-
const {AIMessageConversationDetailID} = await this.FinishConversationAndNotifyUser(apiResponse, md, user, convoEntity, pubSub, userPayload);
|
|
164
|
-
|
|
165
|
-
return {
|
|
166
|
-
Success: true,
|
|
167
|
-
Status: 'OK',
|
|
168
|
-
ConversationId: ConversationId,
|
|
169
|
-
UserMessageConversationDetailId: convoDetailEntity.ID,
|
|
170
|
-
AIMessageConversationDetailId: AIMessageConversationDetailID,
|
|
171
|
-
Result: JSON.stringify(response.data)
|
|
172
|
-
};
|
|
173
192
|
}
|
|
174
193
|
else {
|
|
175
194
|
pubSub.publish(PUSH_STATUS_UPDATES_TOPIC, {
|
|
@@ -192,8 +211,66 @@ export class AskSkipResolver {
|
|
|
192
211
|
}
|
|
193
212
|
}
|
|
194
213
|
|
|
195
|
-
protected async HandleDataRequestPhase(apiResponse:
|
|
196
|
-
|
|
214
|
+
protected async HandleDataRequestPhase(apiRequest: SkipAPIRequest, apiResponse: SkipAPIDataRequestResponse, UserQuestion: string, user: UserInfo, dataSource: DataSource, ConversationId: number, userPayload: UserPayload, pubSub: PubSubEngine): Promise<AskSkipResultType> {
|
|
215
|
+
// our job in this method is to go through each of the data requests from the Skip API, get the data, and then go back to the Skip API again and to the next phase
|
|
216
|
+
try {
|
|
217
|
+
pubSub.publish(PUSH_STATUS_UPDATES_TOPIC, {
|
|
218
|
+
message: JSON.stringify({
|
|
219
|
+
type: 'AskSkip',
|
|
220
|
+
status: 'OK',
|
|
221
|
+
message: 'I am gathering some data needed for your request, once that\'s done I\'ll analyze it for you...',
|
|
222
|
+
}),
|
|
223
|
+
sessionId: userPayload.sessionId,
|
|
224
|
+
});
|
|
225
|
+
|
|
226
|
+
const md = new Metadata();
|
|
227
|
+
for (const dr of apiResponse.dataRequest) {
|
|
228
|
+
switch (dr.type) {
|
|
229
|
+
case "sql":
|
|
230
|
+
const sql = dr.text;
|
|
231
|
+
const result = await dataSource.query(sql);
|
|
232
|
+
if (!result)
|
|
233
|
+
throw new Error(`Error running SQL: ${sql}`);
|
|
234
|
+
|
|
235
|
+
const item = new SkipDataContextItem();
|
|
236
|
+
item.Type = 'sql';
|
|
237
|
+
item.Data = result;
|
|
238
|
+
item.RecordName = dr.text;
|
|
239
|
+
item.AdditionalDescription = dr.description;
|
|
240
|
+
apiRequest.dataContext.Items.push(item);
|
|
241
|
+
break;
|
|
242
|
+
case "stored_query":
|
|
243
|
+
const queryName = dr.text;
|
|
244
|
+
const query = md.Queries.find((q) => q.Name === queryName);
|
|
245
|
+
if (query) {
|
|
246
|
+
const rq = new RunQuery();
|
|
247
|
+
const result = await rq.RunQuery({QueryID: query.ID}, user)
|
|
248
|
+
if (result && result.Success) {
|
|
249
|
+
const item = new SkipDataContextItem();
|
|
250
|
+
item.Type = 'query';
|
|
251
|
+
item.Data = result.Results;
|
|
252
|
+
item.RecordID = query.ID;
|
|
253
|
+
item.RecordName = query.Name;
|
|
254
|
+
item.AdditionalDescription = dr.description;
|
|
255
|
+
apiRequest.dataContext.Items.push(item);
|
|
256
|
+
}
|
|
257
|
+
else
|
|
258
|
+
throw new Error(`Error running query ${queryName}`);
|
|
259
|
+
}
|
|
260
|
+
else
|
|
261
|
+
throw new Error(`Query ${queryName} not found.`);
|
|
262
|
+
break;
|
|
263
|
+
}
|
|
264
|
+
}
|
|
265
|
+
|
|
266
|
+
// we have all of the data now, add it to the data context and then submit it back to the Skip API
|
|
267
|
+
apiRequest.requestPhase = 'data_gathering_response';
|
|
268
|
+
return this.HandleSkipRequest(apiRequest, UserQuestion, user, dataSource, ConversationId, userPayload, pubSub, md, null, null);
|
|
269
|
+
}
|
|
270
|
+
catch (e) {
|
|
271
|
+
LogError(e);
|
|
272
|
+
throw e;
|
|
273
|
+
}
|
|
197
274
|
}
|
|
198
275
|
|
|
199
276
|
/**
|
|
@@ -252,6 +329,15 @@ export class AskSkipResolver {
|
|
|
252
329
|
AIMessageConversationDetailID: convoDetailEntityAI.ID
|
|
253
330
|
};
|
|
254
331
|
}
|
|
332
|
+
|
|
333
|
+
protected async getViewData(ViewId: number, user: UserInfo): Promise<any> {
|
|
334
|
+
const rv = new RunView();
|
|
335
|
+
const result = await rv.RunView({ViewID: ViewId, IgnoreMaxRows: true}, user);
|
|
336
|
+
if (result && result.Success)
|
|
337
|
+
return result.Results;
|
|
338
|
+
else
|
|
339
|
+
throw new Error(`Error running view ${ViewId}`);
|
|
340
|
+
}
|
|
255
341
|
}
|
|
256
342
|
|
|
257
343
|
export default AskSkipResolver;
|