@chrryai/waffles 1.2.80 → 1.2.84
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/index.d.mts +3 -79
- package/dist/index.d.ts +3 -79
- package/dist/index.js +6 -1476
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +7 -1468
- package/dist/index.mjs.map +1 -1
- package/package.json +5 -4
package/dist/index.mjs
CHANGED
|
@@ -1,13 +1,9 @@
|
|
|
1
1
|
import * as dotenv from 'dotenv';
|
|
2
|
-
import { expect } from '@playwright/test';
|
|
3
|
-
import path from 'path';
|
|
4
|
-
import process2 from 'process';
|
|
5
|
-
import { faker } from '@faker-js/faker';
|
|
6
2
|
|
|
7
|
-
// src/
|
|
8
|
-
var TEST_GUEST_FINGERPRINTS =
|
|
9
|
-
var TEST_MEMBER_FINGERPRINTS =
|
|
10
|
-
var TEST_MEMBER_EMAILS =
|
|
3
|
+
// src/index.ts
|
|
4
|
+
var TEST_GUEST_FINGERPRINTS = process.env.TEST_GUEST_FINGERPRINTS?.split(",") || [];
|
|
5
|
+
var TEST_MEMBER_FINGERPRINTS = process.env.TEST_MEMBER_FINGERPRINTS?.split(",") || [];
|
|
6
|
+
var TEST_MEMBER_EMAILS = process.env.TEST_MEMBER_EMAILS?.split(",") || [];
|
|
11
7
|
var VEX_TEST_EMAIL = process.env.VEX_TEST_EMAIL_1;
|
|
12
8
|
var VEX_TEST_PASSWORD = process.env.VEX_TEST_PASSWORD_1;
|
|
13
9
|
var VEX_TEST_FINGERPRINT = TEST_MEMBER_FINGERPRINTS[0];
|
|
@@ -25,7 +21,7 @@ var isCI = process.env.NEXT_PUBLIC_CI || process.env.CI;
|
|
|
25
21
|
var getURL = ({
|
|
26
22
|
isLive = false,
|
|
27
23
|
isMember = false,
|
|
28
|
-
path
|
|
24
|
+
path = "",
|
|
29
25
|
fingerprint = ""
|
|
30
26
|
} = {
|
|
31
27
|
isLive: false,
|
|
@@ -34,7 +30,7 @@ var getURL = ({
|
|
|
34
30
|
fingerprint: ""
|
|
35
31
|
}) => {
|
|
36
32
|
const base = isLive ? LIVE_URL : TEST_URL;
|
|
37
|
-
return isMember ? `${base}${
|
|
33
|
+
return isMember ? `${base}${path}?fp=${fingerprint || TEST_MEMBER_FINGERPRINTS[0]}` : `${base}${path}?fp=${fingerprint || TEST_GUEST_FINGERPRINTS[0]}`;
|
|
38
34
|
};
|
|
39
35
|
var simulateInputPaste = async (page, text) => {
|
|
40
36
|
await page.evaluate((content) => {
|
|
@@ -81,1464 +77,7 @@ var simulatePaste = async (page, text) => {
|
|
|
81
77
|
function capitalizeFirstLetter(val) {
|
|
82
78
|
return String(val).charAt(0).toUpperCase() + String(val).slice(1);
|
|
83
79
|
}
|
|
84
|
-
var chat = async ({
|
|
85
|
-
artifacts,
|
|
86
|
-
page,
|
|
87
|
-
isMember,
|
|
88
|
-
isSubscriber,
|
|
89
|
-
instruction = "This thread will be all about React Native, are you ready?",
|
|
90
|
-
prompts = [
|
|
91
|
-
{
|
|
92
|
-
stop: false,
|
|
93
|
-
text: "Hello",
|
|
94
|
-
agentMessageTimeout: 5e5,
|
|
95
|
-
webSearch: false,
|
|
96
|
-
delete: true,
|
|
97
|
-
mix: {
|
|
98
|
-
image: 0,
|
|
99
|
-
video: 0,
|
|
100
|
-
audio: 0,
|
|
101
|
-
paste: 0,
|
|
102
|
-
pdf: 0
|
|
103
|
-
}
|
|
104
|
-
}
|
|
105
|
-
],
|
|
106
|
-
agentMessageTimeout = 50 * 1e3,
|
|
107
|
-
isNewChat = true,
|
|
108
|
-
isLiveTest = false,
|
|
109
|
-
threadId,
|
|
110
|
-
creditsConsumed = 0,
|
|
111
|
-
bookmark = true
|
|
112
|
-
}) => {
|
|
113
|
-
page.on("console", (msg) => {
|
|
114
|
-
console.log(`[browser][${msg.type()}] ${msg.text()}`, msg);
|
|
115
|
-
});
|
|
116
|
-
if (threadId) {
|
|
117
|
-
instruction = "";
|
|
118
|
-
}
|
|
119
|
-
const hourlyLimit = isSubscriber ? 100 : isMember ? 30 : 10;
|
|
120
|
-
const getModelCredits = (model) => model === "flux" ? 2 : isMember ? model === "chatGPT" ? 4 : model === "deepSeek" ? 1 : model === "claude" ? 3 : 1 : 1;
|
|
121
|
-
const MAX_FILE_SIZE = 4;
|
|
122
|
-
if (prompts?.some(
|
|
123
|
-
(p) => p.pdf && p.pdf > MAX_FILE_SIZE || p.image && p.image > MAX_FILE_SIZE || p.video && p.video > MAX_FILE_SIZE || p.audio && p.audio > MAX_FILE_SIZE || p.paste && p.paste > MAX_FILE_SIZE || Object.values(p.mix || {}).some((v) => v > MAX_FILE_SIZE)
|
|
124
|
-
)) {
|
|
125
|
-
throw new Error("Test file size limit exceeded");
|
|
126
|
-
}
|
|
127
|
-
if (isLiveTest) {
|
|
128
|
-
await page.goto(getURL({ isLive: true, isMember }), {
|
|
129
|
-
waitUntil: "networkidle"
|
|
130
|
-
});
|
|
131
|
-
await wait(3e3);
|
|
132
|
-
} else if (isNewChat) {
|
|
133
|
-
await page.goto(getURL({ isLive: false, isMember }), {
|
|
134
|
-
waitUntil: "networkidle"
|
|
135
|
-
});
|
|
136
|
-
await wait(3e3);
|
|
137
|
-
}
|
|
138
|
-
let credits = isSubscriber ? 2e3 : (isMember ? 150 : 30) - creditsConsumed;
|
|
139
|
-
let hourlyUsage = creditsConsumed || 0;
|
|
140
|
-
const agentModal = page.getByTestId("agent-modal");
|
|
141
|
-
await expect(agentModal).not.toBeVisible();
|
|
142
|
-
const signInModal = page.getByTestId("sign-in-modal");
|
|
143
|
-
await expect(signInModal).not.toBeVisible();
|
|
144
|
-
const agentSelectButton = page.getByTestId("agent-select-button");
|
|
145
|
-
await expect(agentSelectButton).toBeVisible();
|
|
146
|
-
const addDebateAgentButton = page.getByTestId("add-debate-agent-button");
|
|
147
|
-
await expect(addDebateAgentButton).toBeVisible();
|
|
148
|
-
const getAgentName = async () => {
|
|
149
|
-
return page.getByTestId("agent-select-button").getAttribute("data-agent-name");
|
|
150
|
-
};
|
|
151
|
-
const getDebateAgentName = async () => {
|
|
152
|
-
return page.getByTestId("add-debate-agent-button").getAttribute("data-agent-name");
|
|
153
|
-
};
|
|
154
|
-
!isMember && expect(await getAgentName()).toBe("deepSeek");
|
|
155
|
-
const chatTextarea = page.getByTestId("chat-textarea");
|
|
156
|
-
await expect(chatTextarea).toBeVisible();
|
|
157
|
-
const creditsInfo = page.getByTestId("credits-info");
|
|
158
|
-
await expect(creditsInfo).toBeVisible();
|
|
159
|
-
const scrollToBottom = async () => {
|
|
160
|
-
await page.evaluate(() => {
|
|
161
|
-
window.scrollTo(0, document.body.scrollHeight);
|
|
162
|
-
});
|
|
163
|
-
await wait(500);
|
|
164
|
-
};
|
|
165
|
-
const getCreditsLeft = async () => {
|
|
166
|
-
await scrollToBottom();
|
|
167
|
-
const creditsInfo2 = page.getByTestId("credits-info");
|
|
168
|
-
const isCreditsVisible = await creditsInfo2.isVisible().catch(() => false);
|
|
169
|
-
if (!isCreditsVisible) {
|
|
170
|
-
return null;
|
|
171
|
-
}
|
|
172
|
-
return await creditsInfo2.getAttribute("data-credits-left", {
|
|
173
|
-
timeout: 1e3
|
|
174
|
-
});
|
|
175
|
-
};
|
|
176
|
-
const getHourlyUsageLeft = async () => {
|
|
177
|
-
await scrollToBottom();
|
|
178
|
-
const hourlyLimitInfo = page.getByTestId("hourly-limit-info");
|
|
179
|
-
return await hourlyLimitInfo.getAttribute("data-hourly-left", {
|
|
180
|
-
timeout: 1e3
|
|
181
|
-
});
|
|
182
|
-
};
|
|
183
|
-
const subscribeButton = page.getByTestId("subscribe-from-chat-button");
|
|
184
|
-
await expect(subscribeButton).toBeVisible();
|
|
185
|
-
expect(await getCreditsLeft()).toBe(credits.toString());
|
|
186
|
-
const thread2 = page.getByTestId("thread");
|
|
187
|
-
let willFail = false;
|
|
188
|
-
const why = page.getByTestId("instruction-why");
|
|
189
|
-
let instructionButton = page.getByTestId("instruction-button");
|
|
190
|
-
let artifactsButton = page.getByTestId("instruction-artifacts-button");
|
|
191
|
-
if (!threadId) {
|
|
192
|
-
await expect(thread2).not.toBeVisible();
|
|
193
|
-
await expect(why).toBeVisible();
|
|
194
|
-
} else {
|
|
195
|
-
await expect(instructionButton).not.toBeVisible();
|
|
196
|
-
instructionButton = page.getByTestId("chat-instruction-button");
|
|
197
|
-
artifactsButton = page.getByTestId("chat-artifacts-button");
|
|
198
|
-
await expect(thread2).toBeVisible();
|
|
199
|
-
await expect(why).not.toBeVisible();
|
|
200
|
-
}
|
|
201
|
-
await expect(instructionButton).toBeVisible();
|
|
202
|
-
const instructionModal = page.getByTestId("instruction-modal");
|
|
203
|
-
await expect(instructionModal).not.toBeVisible();
|
|
204
|
-
if (instruction) {
|
|
205
|
-
await instructionButton.click();
|
|
206
|
-
await expect(instructionModal).toBeVisible();
|
|
207
|
-
const modalMaxCharCount = page.getByTestId(
|
|
208
|
-
"instruction-modal-max-char-count"
|
|
209
|
-
);
|
|
210
|
-
await expect(modalMaxCharCount).toBeVisible();
|
|
211
|
-
const modalTextarea = page.getByTestId("instruction-modal-textarea");
|
|
212
|
-
await expect(modalTextarea).toBeVisible();
|
|
213
|
-
await modalTextarea.fill(instruction);
|
|
214
|
-
const modalCharLeft = page.getByTestId("instruction-modal-char-left");
|
|
215
|
-
await expect(modalCharLeft).toBeVisible();
|
|
216
|
-
await expect(modalMaxCharCount).not.toBeVisible();
|
|
217
|
-
const modalSaveButton = page.getByTestId("instruction-modal-save-button");
|
|
218
|
-
await expect(modalSaveButton).toBeVisible();
|
|
219
|
-
await modalSaveButton.click();
|
|
220
|
-
}
|
|
221
|
-
if (artifacts) {
|
|
222
|
-
await artifactsButton.click();
|
|
223
|
-
const dataTestId = threadId ? "chat" : "instruction";
|
|
224
|
-
await expect(instructionModal).toBeVisible();
|
|
225
|
-
if (artifacts.pdf) {
|
|
226
|
-
const fileChooserPromise = page.waitForEvent("filechooser");
|
|
227
|
-
await page.getByTestId(`${dataTestId}-artifacts-upload-button`).click();
|
|
228
|
-
const testUsedPaths = Array.from({ length: artifacts.pdf }, (_, i) => {
|
|
229
|
-
const fileType = "pdf";
|
|
230
|
-
const fileName = `test${capitalizeFirstLetter(fileType)}${i + 1}`;
|
|
231
|
-
const extension = "pdf";
|
|
232
|
-
return path.join(
|
|
233
|
-
process2.cwd(),
|
|
234
|
-
"tests/shared",
|
|
235
|
-
fileType,
|
|
236
|
-
`${fileName}.${extension}`
|
|
237
|
-
);
|
|
238
|
-
});
|
|
239
|
-
const fileChooser = await fileChooserPromise;
|
|
240
|
-
await fileChooser.setFiles(testUsedPaths);
|
|
241
|
-
}
|
|
242
|
-
if (artifacts.paste) {
|
|
243
|
-
for (let i = 0; i < artifacts.paste; i++) {
|
|
244
|
-
await simulatePaste(page, faker.lorem.sentence({ min: 550, max: 750 }));
|
|
245
|
-
}
|
|
246
|
-
}
|
|
247
|
-
if ((artifacts.pdf || 0) + (artifacts.paste || 0) > 5) {
|
|
248
|
-
await expect(page.getByText("Maximum 5 files allowed")).toBeVisible();
|
|
249
|
-
}
|
|
250
|
-
const modalSaveButton = page.getByTestId(`${dataTestId}-modal-save-button`);
|
|
251
|
-
await expect(modalSaveButton).toBeVisible();
|
|
252
|
-
await modalSaveButton.click();
|
|
253
|
-
expect(await page.getByText("Updated").count()).toBeGreaterThan(0);
|
|
254
|
-
}
|
|
255
|
-
const getAgentModalButton = (agent) => {
|
|
256
|
-
const agentModalButton = page.getByTestId(`agent-modal-button-${agent}`);
|
|
257
|
-
return agentModalButton;
|
|
258
|
-
};
|
|
259
|
-
for (const prompt of prompts) {
|
|
260
|
-
const debateAgentDeleteButton = page.getByTestId(
|
|
261
|
-
"debate-agent-delete-button"
|
|
262
|
-
);
|
|
263
|
-
const isDebateAgentVisible = await debateAgentDeleteButton.isVisible();
|
|
264
|
-
if (isDebateAgentVisible) {
|
|
265
|
-
await debateAgentDeleteButton.click();
|
|
266
|
-
}
|
|
267
|
-
if (prompt.model && prompt.model !== await getAgentName()) {
|
|
268
|
-
await agentSelectButton.click();
|
|
269
|
-
await expect(agentModal).toBeVisible();
|
|
270
|
-
const agentModalButton = getAgentModalButton(prompt.model);
|
|
271
|
-
await agentModalButton.click();
|
|
272
|
-
if (prompt.model === "gemini") {
|
|
273
|
-
const agentModalCloseButton = page.getByTestId(
|
|
274
|
-
"agent-modal-close-button"
|
|
275
|
-
);
|
|
276
|
-
await expect(agentModalCloseButton).toBeVisible();
|
|
277
|
-
await agentModalCloseButton.click();
|
|
278
|
-
expect(await getAgentName()).toBe(isMember ? "chatGPT" : "flux");
|
|
279
|
-
} else {
|
|
280
|
-
if (!isMember) {
|
|
281
|
-
if (!["flux", "deepSeek", "gemini"].includes(prompt.model)) {
|
|
282
|
-
await expect(signInModal).toBeVisible();
|
|
283
|
-
const signInModalCloseButton = page.getByTestId(
|
|
284
|
-
"sign-in-modal-close-button"
|
|
285
|
-
);
|
|
286
|
-
await expect(signInModalCloseButton).toBeVisible();
|
|
287
|
-
await signInModalCloseButton.click();
|
|
288
|
-
expect(await getAgentName()).toBe("deepSeek");
|
|
289
|
-
}
|
|
290
|
-
} else {
|
|
291
|
-
expect(await getAgentName()).toBe(prompt.model);
|
|
292
|
-
}
|
|
293
|
-
}
|
|
294
|
-
}
|
|
295
|
-
if (prompt.debateAgent) {
|
|
296
|
-
{
|
|
297
|
-
await addDebateAgentButton.click();
|
|
298
|
-
await expect(agentModal).toBeVisible();
|
|
299
|
-
const geminiButton = page.getByTestId(`agent-modal-button-gemini`);
|
|
300
|
-
const fluxButton = page.getByTestId(`agent-modal-button-flux`);
|
|
301
|
-
expect(geminiButton).not.toBeVisible();
|
|
302
|
-
expect(fluxButton).not.toBeVisible();
|
|
303
|
-
const agentModalButton = page.getByTestId(
|
|
304
|
-
`agent-modal-button-${prompt.debateAgent}`
|
|
305
|
-
);
|
|
306
|
-
await agentModalButton.click();
|
|
307
|
-
}
|
|
308
|
-
if (!isMember) {
|
|
309
|
-
expect(prompt.shouldFail).toBe(true);
|
|
310
|
-
willFail = true;
|
|
311
|
-
} else {
|
|
312
|
-
expect(await getDebateAgentName()).toBe(prompt.debateAgent);
|
|
313
|
-
await addDebateAgentButton.click();
|
|
314
|
-
await expect(getAgentModalButton(prompt.debateAgent)).not.toBeVisible();
|
|
315
|
-
const agentModalCloseButton = page.getByTestId(
|
|
316
|
-
"agent-modal-close-button"
|
|
317
|
-
);
|
|
318
|
-
await expect(agentModalCloseButton).toBeVisible();
|
|
319
|
-
await agentModalCloseButton.click();
|
|
320
|
-
await agentSelectButton.click();
|
|
321
|
-
await expect(agentModal).toBeVisible();
|
|
322
|
-
const fluxButton = getAgentModalButton("flux");
|
|
323
|
-
await expect(fluxButton).toBeVisible();
|
|
324
|
-
await fluxButton.click();
|
|
325
|
-
await wait(1e3);
|
|
326
|
-
await expect(addDebateAgentButton).not.toBeVisible();
|
|
327
|
-
await agentSelectButton.click();
|
|
328
|
-
const promptAgentModalButton = page.getByTestId(
|
|
329
|
-
`agent-modal-button-${prompt.model}`
|
|
330
|
-
);
|
|
331
|
-
await promptAgentModalButton.click();
|
|
332
|
-
expect(await getAgentName()).toBe(prompt.model);
|
|
333
|
-
await addDebateAgentButton.click();
|
|
334
|
-
await expect(addDebateAgentButton).toBeVisible();
|
|
335
|
-
await getAgentModalButton(prompt.debateAgent).click();
|
|
336
|
-
expect(await getDebateAgentName()).toBe(prompt.debateAgent);
|
|
337
|
-
expect(await getAgentName()).toBe(prompt.model);
|
|
338
|
-
}
|
|
339
|
-
}
|
|
340
|
-
if (willFail) {
|
|
341
|
-
return;
|
|
342
|
-
}
|
|
343
|
-
const attachButton = page.getByTestId("attach-button");
|
|
344
|
-
const attachButtonClose = page.getByTestId("attach-button-close");
|
|
345
|
-
const attachButtonImage = page.getByTestId("attach-button-image");
|
|
346
|
-
const attachButtonVideo = page.getByTestId("attach-button-video");
|
|
347
|
-
const attachButtonAudio = page.getByTestId("attach-button-audio");
|
|
348
|
-
const attachButtonPdf = page.getByTestId("attach-button-pdf");
|
|
349
|
-
if (prompt.image) {
|
|
350
|
-
for (let i = 0; i < prompt.image; i++) {
|
|
351
|
-
attachButton.click();
|
|
352
|
-
await wait(1e3);
|
|
353
|
-
await expect(attachButton).not.toBeVisible();
|
|
354
|
-
await expect(attachButtonClose).toBeVisible();
|
|
355
|
-
await expect(attachButtonImage).toBeVisible();
|
|
356
|
-
await expect(attachButtonVideo).toBeVisible();
|
|
357
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
358
|
-
await expect(attachButtonPdf).toBeVisible();
|
|
359
|
-
const fileChooserPromise2 = page.waitForEvent("filechooser");
|
|
360
|
-
if (i === 3) {
|
|
361
|
-
await expect(attachButtonImage).toBeDisabled();
|
|
362
|
-
await expect(attachButtonVideo).toBeDisabled();
|
|
363
|
-
await expect(attachButtonAudio).toBeDisabled();
|
|
364
|
-
await expect(attachButtonPdf).toBeDisabled();
|
|
365
|
-
await attachButtonClose.click();
|
|
366
|
-
await expect(attachButton).toBeVisible();
|
|
367
|
-
break;
|
|
368
|
-
}
|
|
369
|
-
await attachButtonImage.click();
|
|
370
|
-
{
|
|
371
|
-
const fileChooser2 = await fileChooserPromise2;
|
|
372
|
-
const testUsed = path.join(
|
|
373
|
-
process2.cwd(),
|
|
374
|
-
`tests/shared/image/testImage${i + 1}.jpeg`
|
|
375
|
-
);
|
|
376
|
-
await fileChooser2.setFiles(testUsed);
|
|
377
|
-
await page.waitForTimeout(2e3);
|
|
378
|
-
await expect(attachButton).toBeVisible();
|
|
379
|
-
attachButton.click();
|
|
380
|
-
await expect(attachButtonImage).toBeVisible();
|
|
381
|
-
await expect(attachButtonVideo).toBeVisible();
|
|
382
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
383
|
-
await expect(attachButtonPdf).toBeVisible();
|
|
384
|
-
await attachButtonClose.click();
|
|
385
|
-
await expect(attachButton).toBeVisible();
|
|
386
|
-
}
|
|
387
|
-
}
|
|
388
|
-
const filePreviewClears = page.getByTestId("file-preview-clear");
|
|
389
|
-
const count = prompt.image > 3 ? 3 : prompt.image;
|
|
390
|
-
for (let i = 0; i < count; i++) {
|
|
391
|
-
const filePreviewClear = filePreviewClears.nth(count - i - 1);
|
|
392
|
-
await expect(filePreviewClear).toBeVisible();
|
|
393
|
-
await filePreviewClear.click();
|
|
394
|
-
await page.waitForTimeout(500);
|
|
395
|
-
}
|
|
396
|
-
await expect(attachButton).toBeVisible();
|
|
397
|
-
attachButton.click();
|
|
398
|
-
const fileChooserPromise = page.waitForEvent("filechooser");
|
|
399
|
-
await expect(attachButtonImage).toBeVisible();
|
|
400
|
-
await attachButtonImage.click();
|
|
401
|
-
const fileChooser = await fileChooserPromise;
|
|
402
|
-
const testUsedPaths = Array.from(
|
|
403
|
-
{ length: prompt.image },
|
|
404
|
-
(_, i) => path.join(
|
|
405
|
-
process2.cwd(),
|
|
406
|
-
"tests/shared/image",
|
|
407
|
-
`testImage${i + 1}.jpeg`
|
|
408
|
-
)
|
|
409
|
-
);
|
|
410
|
-
await fileChooser.setFiles(testUsedPaths);
|
|
411
|
-
if (prompt.image > 3) {
|
|
412
|
-
await expect(page.getByText("Too many files selected")).toBeVisible();
|
|
413
|
-
}
|
|
414
|
-
} else if (prompt.audio) {
|
|
415
|
-
for (let i = 0; i < prompt.audio; i++) {
|
|
416
|
-
attachButton.click();
|
|
417
|
-
await wait(1e3);
|
|
418
|
-
await expect(attachButton).not.toBeVisible();
|
|
419
|
-
await expect(attachButtonClose).toBeVisible();
|
|
420
|
-
await expect(attachButtonImage).toBeVisible();
|
|
421
|
-
await expect(attachButtonVideo).toBeVisible();
|
|
422
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
423
|
-
await expect(attachButtonPdf).toBeVisible();
|
|
424
|
-
const fileChooserPromise2 = page.waitForEvent("filechooser");
|
|
425
|
-
if (i === 3) {
|
|
426
|
-
await expect(attachButtonImage).toBeDisabled();
|
|
427
|
-
await expect(attachButtonVideo).toBeDisabled();
|
|
428
|
-
await expect(attachButtonAudio).toBeDisabled();
|
|
429
|
-
await expect(attachButtonPdf).toBeDisabled();
|
|
430
|
-
await attachButtonClose.click();
|
|
431
|
-
await expect(attachButton).toBeVisible();
|
|
432
|
-
break;
|
|
433
|
-
}
|
|
434
|
-
await attachButtonAudio.click();
|
|
435
|
-
{
|
|
436
|
-
const fileChooser2 = await fileChooserPromise2;
|
|
437
|
-
const testUsed = path.join(
|
|
438
|
-
process2.cwd(),
|
|
439
|
-
`tests/shared/audio/testAudio${i + 1}.wav`
|
|
440
|
-
);
|
|
441
|
-
await fileChooser2.setFiles(testUsed);
|
|
442
|
-
await page.waitForTimeout(2e3);
|
|
443
|
-
await expect(attachButton).toBeVisible();
|
|
444
|
-
attachButton.click();
|
|
445
|
-
await expect(attachButtonImage).toBeVisible();
|
|
446
|
-
await expect(attachButtonVideo).toBeVisible();
|
|
447
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
448
|
-
await expect(attachButtonPdf).toBeVisible();
|
|
449
|
-
await attachButtonClose.click();
|
|
450
|
-
await expect(attachButton).toBeVisible();
|
|
451
|
-
}
|
|
452
|
-
}
|
|
453
|
-
const filePreviewClears = page.getByTestId("file-preview-clear");
|
|
454
|
-
const count = prompt.audio > 3 ? 3 : prompt.audio;
|
|
455
|
-
for (let i = 0; i < count; i++) {
|
|
456
|
-
const filePreviewClear = filePreviewClears.nth(count - i - 1);
|
|
457
|
-
await expect(filePreviewClear).toBeVisible();
|
|
458
|
-
await filePreviewClear.click();
|
|
459
|
-
await page.waitForTimeout(500);
|
|
460
|
-
}
|
|
461
|
-
await expect(attachButton).toBeVisible();
|
|
462
|
-
attachButton.click();
|
|
463
|
-
const fileChooserPromise = page.waitForEvent("filechooser");
|
|
464
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
465
|
-
await attachButtonAudio.click();
|
|
466
|
-
const fileChooser = await fileChooserPromise;
|
|
467
|
-
const testUsedPaths = Array.from(
|
|
468
|
-
{ length: prompt.audio },
|
|
469
|
-
(_, i) => path.join(process2.cwd(), "tests/shared/audio", `testAudio${i + 1}.wav`)
|
|
470
|
-
);
|
|
471
|
-
await fileChooser.setFiles(testUsedPaths);
|
|
472
|
-
if (prompt.audio > 3) {
|
|
473
|
-
await expect(page.getByText("Too many files selected")).toBeVisible();
|
|
474
|
-
}
|
|
475
|
-
} else if (prompt.video) {
|
|
476
|
-
for (let i = 0; i < prompt.video; i++) {
|
|
477
|
-
attachButton.click();
|
|
478
|
-
await wait(1e3);
|
|
479
|
-
await expect(attachButton).not.toBeVisible();
|
|
480
|
-
await expect(attachButtonClose).toBeVisible();
|
|
481
|
-
await expect(attachButtonImage).toBeVisible();
|
|
482
|
-
await expect(attachButtonVideo).toBeVisible();
|
|
483
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
484
|
-
await expect(attachButtonPdf).toBeVisible();
|
|
485
|
-
const fileChooserPromise2 = page.waitForEvent("filechooser");
|
|
486
|
-
if (i === 3) {
|
|
487
|
-
await expect(attachButtonImage).toBeDisabled();
|
|
488
|
-
await expect(attachButtonVideo).toBeDisabled();
|
|
489
|
-
await expect(attachButtonAudio).toBeDisabled();
|
|
490
|
-
await expect(attachButtonPdf).toBeDisabled();
|
|
491
|
-
await attachButtonClose.click();
|
|
492
|
-
await expect(attachButton).toBeVisible();
|
|
493
|
-
break;
|
|
494
|
-
}
|
|
495
|
-
await attachButtonAudio.click();
|
|
496
|
-
{
|
|
497
|
-
const fileChooser2 = await fileChooserPromise2;
|
|
498
|
-
const testUsed = path.join(
|
|
499
|
-
process2.cwd(),
|
|
500
|
-
`tests/shared/video/testVideo${i + 1}.webm`
|
|
501
|
-
);
|
|
502
|
-
await fileChooser2.setFiles(testUsed);
|
|
503
|
-
await page.waitForTimeout(2e3);
|
|
504
|
-
await expect(attachButton).toBeVisible();
|
|
505
|
-
attachButton.click();
|
|
506
|
-
await expect(attachButtonImage).toBeVisible();
|
|
507
|
-
await expect(attachButtonVideo).toBeVisible();
|
|
508
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
509
|
-
await expect(attachButtonPdf).toBeVisible();
|
|
510
|
-
await attachButtonClose.click();
|
|
511
|
-
await expect(attachButton).toBeVisible();
|
|
512
|
-
}
|
|
513
|
-
}
|
|
514
|
-
const filePreviewClears = page.getByTestId("file-preview-clear");
|
|
515
|
-
const count = prompt.video > 3 ? 3 : prompt.video;
|
|
516
|
-
for (let i = 0; i < count; i++) {
|
|
517
|
-
const filePreviewClear = filePreviewClears.nth(count - i - 1);
|
|
518
|
-
await expect(filePreviewClear).toBeVisible();
|
|
519
|
-
await filePreviewClear.click();
|
|
520
|
-
await page.waitForTimeout(500);
|
|
521
|
-
}
|
|
522
|
-
await expect(attachButton).toBeVisible();
|
|
523
|
-
attachButton.click();
|
|
524
|
-
const fileChooserPromise = page.waitForEvent("filechooser");
|
|
525
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
526
|
-
await attachButtonAudio.click();
|
|
527
|
-
const fileChooser = await fileChooserPromise;
|
|
528
|
-
const testUsedPaths = Array.from(
|
|
529
|
-
{ length: prompt.video },
|
|
530
|
-
(_, i) => path.join(
|
|
531
|
-
process2.cwd(),
|
|
532
|
-
"tests/shared/video",
|
|
533
|
-
`testVideo${i + 1}.webm`
|
|
534
|
-
)
|
|
535
|
-
);
|
|
536
|
-
await fileChooser.setFiles(testUsedPaths);
|
|
537
|
-
if (prompt.video > 3) {
|
|
538
|
-
await expect(page.getByText("Too many files selected")).toBeVisible();
|
|
539
|
-
}
|
|
540
|
-
} else if (prompt.pdf) {
|
|
541
|
-
for (let i = 0; i < prompt.pdf; i++) {
|
|
542
|
-
attachButton.click();
|
|
543
|
-
await wait(1e3);
|
|
544
|
-
await expect(attachButton).not.toBeVisible();
|
|
545
|
-
await expect(attachButtonClose).toBeVisible();
|
|
546
|
-
await expect(attachButtonImage).toBeVisible();
|
|
547
|
-
await expect(attachButtonVideo).toBeVisible();
|
|
548
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
549
|
-
await expect(attachButtonPdf).toBeVisible();
|
|
550
|
-
const fileChooserPromise2 = page.waitForEvent("filechooser");
|
|
551
|
-
if (i === 3) {
|
|
552
|
-
await expect(attachButtonImage).toBeDisabled();
|
|
553
|
-
await expect(attachButtonVideo).toBeDisabled();
|
|
554
|
-
await expect(attachButtonAudio).toBeDisabled();
|
|
555
|
-
await expect(attachButtonPdf).toBeDisabled();
|
|
556
|
-
await attachButtonClose.click();
|
|
557
|
-
await expect(attachButton).toBeVisible();
|
|
558
|
-
break;
|
|
559
|
-
}
|
|
560
|
-
await attachButtonPdf.click();
|
|
561
|
-
{
|
|
562
|
-
const fileChooser2 = await fileChooserPromise2;
|
|
563
|
-
const testUsed = path.join(
|
|
564
|
-
process2.cwd(),
|
|
565
|
-
`tests/shared/pdf/testPdf${i + 1}.pdf`
|
|
566
|
-
);
|
|
567
|
-
await fileChooser2.setFiles(testUsed);
|
|
568
|
-
await page.waitForTimeout(2e3);
|
|
569
|
-
await expect(attachButton).toBeVisible();
|
|
570
|
-
attachButton.click();
|
|
571
|
-
await expect(attachButtonImage).toBeVisible();
|
|
572
|
-
await expect(attachButtonVideo).toBeVisible();
|
|
573
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
574
|
-
await expect(attachButtonPdf).toBeVisible();
|
|
575
|
-
await attachButtonClose.click();
|
|
576
|
-
await expect(attachButton).toBeVisible();
|
|
577
|
-
}
|
|
578
|
-
}
|
|
579
|
-
const filePreviewClears = page.getByTestId("file-preview-clear");
|
|
580
|
-
const count = prompt.pdf > 3 ? 3 : prompt.pdf;
|
|
581
|
-
for (let i = 0; i < count; i++) {
|
|
582
|
-
const filePreviewClear = filePreviewClears.nth(count - i - 1);
|
|
583
|
-
await expect(filePreviewClear).toBeVisible();
|
|
584
|
-
await filePreviewClear.click();
|
|
585
|
-
await page.waitForTimeout(500);
|
|
586
|
-
}
|
|
587
|
-
await expect(attachButton).toBeVisible();
|
|
588
|
-
attachButton.click();
|
|
589
|
-
const fileChooserPromise = page.waitForEvent("filechooser");
|
|
590
|
-
await expect(attachButtonPdf).toBeVisible();
|
|
591
|
-
await attachButtonPdf.click();
|
|
592
|
-
const fileChooser = await fileChooserPromise;
|
|
593
|
-
const testUsedPaths = Array.from(
|
|
594
|
-
{ length: prompt.pdf },
|
|
595
|
-
(_, i) => path.join(process2.cwd(), "tests/shared/pdf", `testPdf${i + 1}.pdf`)
|
|
596
|
-
);
|
|
597
|
-
await fileChooser.setFiles(testUsedPaths);
|
|
598
|
-
if (prompt.pdf > 3) {
|
|
599
|
-
await expect(page.getByText("Too many files selected")).toBeVisible();
|
|
600
|
-
}
|
|
601
|
-
} else if (prompt.paste) {
|
|
602
|
-
const filePreviewClears = page.getByTestId("file-preview-clear");
|
|
603
|
-
const count = prompt.paste > 3 ? 3 : prompt.paste;
|
|
604
|
-
for (let i = 0; i < prompt.paste; i++) {
|
|
605
|
-
const text = faker.lorem.sentence({ min: 550, max: 750 });
|
|
606
|
-
await simulateInputPaste(page, text);
|
|
607
|
-
await page.waitForTimeout(1e3);
|
|
608
|
-
}
|
|
609
|
-
if (prompt.paste > 3) {
|
|
610
|
-
await expect(page.getByText("Too many files")).toBeVisible();
|
|
611
|
-
}
|
|
612
|
-
for (let i = 0; i < count; i++) {
|
|
613
|
-
const filePreviewClear = filePreviewClears.nth(count - i - 1);
|
|
614
|
-
await expect(filePreviewClear).toBeVisible();
|
|
615
|
-
await filePreviewClear.click();
|
|
616
|
-
await page.waitForTimeout(500);
|
|
617
|
-
}
|
|
618
|
-
for (let i = 0; i < count; i++) {
|
|
619
|
-
const text = faker.lorem.sentence({ min: 550, max: 750 });
|
|
620
|
-
await simulateInputPaste(page, text);
|
|
621
|
-
}
|
|
622
|
-
} else if (prompt.mix) {
|
|
623
|
-
const fileExtensions = {
|
|
624
|
-
image: "jpeg",
|
|
625
|
-
video: "mp4",
|
|
626
|
-
audio: "wav",
|
|
627
|
-
pdf: "pdf"
|
|
628
|
-
};
|
|
629
|
-
const size = Object.values(prompt.mix).reduce((a, b) => a + b);
|
|
630
|
-
const to = size > 3 ? 3 : size;
|
|
631
|
-
let filesToAttach = [];
|
|
632
|
-
let filesToPaste = 0;
|
|
633
|
-
for (const [key, count] of Object.entries(prompt.mix)) {
|
|
634
|
-
if (key === "paste") {
|
|
635
|
-
filesToPaste = count;
|
|
636
|
-
} else {
|
|
637
|
-
for (let i = 0; i < count; i++) {
|
|
638
|
-
filesToAttach.push(key);
|
|
639
|
-
}
|
|
640
|
-
}
|
|
641
|
-
}
|
|
642
|
-
filesToAttach = filesToAttach.slice(0, 3 - filesToPaste);
|
|
643
|
-
for (let i = 0; i < filesToPaste; i++) {
|
|
644
|
-
const text = faker.lorem.sentence({ min: 550, max: 750 });
|
|
645
|
-
await simulateInputPaste(page, text);
|
|
646
|
-
await page.waitForTimeout(1e3);
|
|
647
|
-
}
|
|
648
|
-
for (let i = 0; i < filesToAttach.length; i++) {
|
|
649
|
-
const key = filesToAttach[i];
|
|
650
|
-
if (!key) break;
|
|
651
|
-
attachButton.click();
|
|
652
|
-
await wait(1e3);
|
|
653
|
-
await expect(attachButton).not.toBeVisible();
|
|
654
|
-
await expect(attachButtonClose).toBeVisible();
|
|
655
|
-
await expect(attachButtonImage).toBeVisible();
|
|
656
|
-
await expect(attachButtonVideo).toBeVisible();
|
|
657
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
658
|
-
await expect(attachButtonPdf).toBeVisible();
|
|
659
|
-
if (i > to) {
|
|
660
|
-
await expect(attachButtonImage).toBeDisabled();
|
|
661
|
-
await expect(attachButtonVideo).toBeDisabled();
|
|
662
|
-
await expect(attachButtonAudio).toBeDisabled();
|
|
663
|
-
await expect(attachButtonPdf).toBeDisabled();
|
|
664
|
-
await attachButtonClose.click();
|
|
665
|
-
await expect(attachButton).toBeVisible();
|
|
666
|
-
break;
|
|
667
|
-
}
|
|
668
|
-
const fileChooserPromise = page.waitForEvent("filechooser");
|
|
669
|
-
if (key === "audio") {
|
|
670
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
671
|
-
await attachButtonAudio.click();
|
|
672
|
-
} else if (key === "image") {
|
|
673
|
-
await expect(attachButtonImage).toBeVisible();
|
|
674
|
-
await attachButtonImage.click();
|
|
675
|
-
} else if (key === "video") {
|
|
676
|
-
await expect(attachButtonVideo).toBeVisible();
|
|
677
|
-
await attachButtonVideo.click();
|
|
678
|
-
} else if (key === "pdf") {
|
|
679
|
-
await expect(attachButtonPdf).toBeVisible();
|
|
680
|
-
await attachButtonPdf.click();
|
|
681
|
-
}
|
|
682
|
-
{
|
|
683
|
-
const fileChooser = await fileChooserPromise;
|
|
684
|
-
const extension = fileExtensions[key] || "jpeg";
|
|
685
|
-
const fileIndex = filesToAttach.slice(0, i + 1).filter((k) => k === key).length;
|
|
686
|
-
const testUsed = path.join(
|
|
687
|
-
process2.cwd(),
|
|
688
|
-
`tests/shared/${key}/test${capitalizeFirstLetter(key)}${fileIndex}.${extension}`
|
|
689
|
-
);
|
|
690
|
-
await fileChooser.setFiles(testUsed);
|
|
691
|
-
await page.waitForTimeout(2e3);
|
|
692
|
-
await expect(attachButton).toBeVisible();
|
|
693
|
-
attachButton.click();
|
|
694
|
-
await expect(attachButtonImage).toBeVisible();
|
|
695
|
-
await expect(attachButtonVideo).toBeVisible();
|
|
696
|
-
await expect(attachButtonAudio).toBeVisible();
|
|
697
|
-
await expect(attachButtonPdf).toBeVisible();
|
|
698
|
-
await attachButtonClose.click();
|
|
699
|
-
await expect(attachButton).toBeVisible();
|
|
700
|
-
}
|
|
701
|
-
}
|
|
702
|
-
const filePreviewClears = page.getByTestId("file-preview-clear");
|
|
703
|
-
for (let i = 0; i < to; i++) {
|
|
704
|
-
const filePreviewClear = filePreviewClears.nth(0);
|
|
705
|
-
await expect(filePreviewClear).toBeVisible();
|
|
706
|
-
await filePreviewClear.click();
|
|
707
|
-
await page.waitForTimeout(500);
|
|
708
|
-
}
|
|
709
|
-
for (let i = 0; i < filesToPaste; i++) {
|
|
710
|
-
const text = faker.lorem.sentence({ min: 550, max: 750 });
|
|
711
|
-
await simulateInputPaste(page, text);
|
|
712
|
-
await page.waitForTimeout(1e3);
|
|
713
|
-
}
|
|
714
|
-
if (filesToAttach.length > 0) {
|
|
715
|
-
await expect(attachButton).toBeVisible();
|
|
716
|
-
attachButton.click();
|
|
717
|
-
const fileChooserPromise = page.waitForEvent("filechooser");
|
|
718
|
-
const key = filesToAttach[0];
|
|
719
|
-
if (key === "image") {
|
|
720
|
-
await attachButtonImage.click();
|
|
721
|
-
} else if (key === "video") {
|
|
722
|
-
await attachButtonVideo.click();
|
|
723
|
-
} else if (key === "audio") {
|
|
724
|
-
await attachButtonAudio.click();
|
|
725
|
-
} else if (key === "pdf") {
|
|
726
|
-
await attachButtonPdf.click();
|
|
727
|
-
}
|
|
728
|
-
const fileChooser = await fileChooserPromise;
|
|
729
|
-
const testUsedPaths = await Promise.all(
|
|
730
|
-
Array.from({ length: filesToAttach.length }, async (_, i) => {
|
|
731
|
-
const fileType = filesToAttach[i];
|
|
732
|
-
if (!fileType) {
|
|
733
|
-
return null;
|
|
734
|
-
}
|
|
735
|
-
const fileName = `test${capitalizeFirstLetter(fileType)}${i + 1}`;
|
|
736
|
-
const extension = fileExtensions[fileType] || "jpeg";
|
|
737
|
-
return path.join(
|
|
738
|
-
process2.cwd(),
|
|
739
|
-
"tests/shared",
|
|
740
|
-
fileType,
|
|
741
|
-
`${fileName}.${extension}`
|
|
742
|
-
);
|
|
743
|
-
})
|
|
744
|
-
);
|
|
745
|
-
await fileChooser.setFiles(
|
|
746
|
-
testUsedPaths.filter((path2) => path2 !== null)
|
|
747
|
-
);
|
|
748
|
-
if (filesToAttach.length + filesToPaste > 3) {
|
|
749
|
-
await expect(page.getByText("Too many files selected")).toBeVisible();
|
|
750
|
-
}
|
|
751
|
-
}
|
|
752
|
-
}
|
|
753
|
-
await chatTextarea.fill(prompt.text);
|
|
754
|
-
if (prompt.webSearch) {
|
|
755
|
-
const webSearchButton = page.getByTestId("web-search-button-disabled");
|
|
756
|
-
await expect(webSearchButton).toBeVisible();
|
|
757
|
-
await webSearchButton.click();
|
|
758
|
-
if (!isMember) {
|
|
759
|
-
await expect(agentModal).toBeVisible();
|
|
760
|
-
const agentModalCloseButton = page.getByTestId(
|
|
761
|
-
"agent-modal-close-button"
|
|
762
|
-
);
|
|
763
|
-
await expect(agentModalCloseButton).toBeVisible();
|
|
764
|
-
await agentModalCloseButton.click();
|
|
765
|
-
}
|
|
766
|
-
}
|
|
767
|
-
const sendButton = page.getByTestId("chat-send-button");
|
|
768
|
-
await expect(sendButton).toBeVisible();
|
|
769
|
-
if (prompt.shouldFail) {
|
|
770
|
-
console.log(
|
|
771
|
-
`\u{1F6AB} Testing hourly limit boundary with message: "${prompt.text}"`
|
|
772
|
-
);
|
|
773
|
-
await expect(sendButton).toBeDisabled();
|
|
774
|
-
break;
|
|
775
|
-
}
|
|
776
|
-
await scrollToBottom();
|
|
777
|
-
await sendButton.click();
|
|
778
|
-
if (prompts.indexOf(prompt) === 0 && artifacts) {
|
|
779
|
-
await expect(page.getByText("Uploading artifacts...")).toBeVisible();
|
|
780
|
-
}
|
|
781
|
-
await page.waitForTimeout(5e3);
|
|
782
|
-
const stopButton = page.getByTestId("chat-stop-streaming-button");
|
|
783
|
-
await expect(stopButton).toBeVisible({
|
|
784
|
-
timeout: prompt.agentMessageTimeout || agentMessageTimeout
|
|
785
|
-
});
|
|
786
|
-
const getLastMessage = async () => {
|
|
787
|
-
await page.waitForFunction(
|
|
788
|
-
() => {
|
|
789
|
-
const userMessages2 = document.querySelectorAll(
|
|
790
|
-
'[data-testid="user-message"]'
|
|
791
|
-
);
|
|
792
|
-
const guestMessages2 = document.querySelectorAll(
|
|
793
|
-
'[data-testid="guest-message"]'
|
|
794
|
-
);
|
|
795
|
-
console.log(
|
|
796
|
-
`Debug: Found ${userMessages2.length} user messages, ${guestMessages2.length} guest messages`
|
|
797
|
-
);
|
|
798
|
-
return userMessages2.length > 0 || guestMessages2.length > 0;
|
|
799
|
-
},
|
|
800
|
-
{ timeout: 1e4 }
|
|
801
|
-
);
|
|
802
|
-
const userMessages = page.getByTestId("user-message");
|
|
803
|
-
const guestMessages = page.getByTestId("guest-message");
|
|
804
|
-
const userCount = await userMessages.count();
|
|
805
|
-
const guestCount = await guestMessages.count();
|
|
806
|
-
console.log(
|
|
807
|
-
`Debug: After wait - ${userCount} user messages, ${guestCount} guest messages`
|
|
808
|
-
);
|
|
809
|
-
if (userCount > 0) {
|
|
810
|
-
console.log(`Debug: Using user message (${userCount} found)`);
|
|
811
|
-
return userMessages.nth(userCount - 1);
|
|
812
|
-
} else if (guestCount > 0) {
|
|
813
|
-
console.log(`Debug: Using guest message (${guestCount} found)`);
|
|
814
|
-
return guestMessages.nth(guestCount - 1);
|
|
815
|
-
} else {
|
|
816
|
-
throw new Error("No user or guest messages found after waiting");
|
|
817
|
-
}
|
|
818
|
-
};
|
|
819
|
-
await expect(await getLastMessage()).toBeVisible({
|
|
820
|
-
timeout: prompt.agentMessageTimeout || agentMessageTimeout
|
|
821
|
-
});
|
|
822
|
-
const lastMessage = await getLastMessage();
|
|
823
|
-
console.log(`Debug: Got last message, looking for delete button...`);
|
|
824
|
-
if (prompt.stop) {
|
|
825
|
-
await stopButton.click();
|
|
826
|
-
await expect(stopButton).not.toBeVisible({
|
|
827
|
-
timeout: 8e3
|
|
828
|
-
});
|
|
829
|
-
prompt.model && (credits -= getModelCredits(prompt.model));
|
|
830
|
-
} else {
|
|
831
|
-
hourlyUsage += 1 + (prompt.debateAgent ? 1 : 0);
|
|
832
|
-
}
|
|
833
|
-
const deleteMessageButton = lastMessage.locator(
|
|
834
|
-
"[data-testid=delete-message]"
|
|
835
|
-
);
|
|
836
|
-
const deleteButtonCount = await deleteMessageButton.count();
|
|
837
|
-
console.log(
|
|
838
|
-
`Debug: Found ${deleteButtonCount} delete buttons in last message`
|
|
839
|
-
);
|
|
840
|
-
const userMessageContent = (await getLastMessage()).getByText(prompt.text);
|
|
841
|
-
await expect(userMessageContent).toBeVisible({
|
|
842
|
-
timeout: agentMessageTimeout
|
|
843
|
-
});
|
|
844
|
-
const getLastAgentMessage = async () => {
|
|
845
|
-
const agentMessages = page.getByTestId("agent-message");
|
|
846
|
-
const messageCount = await agentMessages.count();
|
|
847
|
-
return agentMessages.nth(messageCount - 1);
|
|
848
|
-
};
|
|
849
|
-
const getLastUserMessage = async () => {
|
|
850
|
-
const userMessages = page.getByTestId(
|
|
851
|
-
`${isMember ? "user" : "guest"}-message`
|
|
852
|
-
);
|
|
853
|
-
const messageCount = await userMessages.count();
|
|
854
|
-
return userMessages.nth(messageCount - 1);
|
|
855
|
-
};
|
|
856
|
-
await expect(await getLastAgentMessage()).toBeVisible();
|
|
857
|
-
const deleteAgentMessageButton = (await getLastAgentMessage()).locator(
|
|
858
|
-
"[data-testid=delete-message]"
|
|
859
|
-
);
|
|
860
|
-
await expect(deleteAgentMessageButton).toBeVisible({
|
|
861
|
-
timeout: prompt.agentMessageTimeout || agentMessageTimeout,
|
|
862
|
-
visible: !prompt.stop
|
|
863
|
-
});
|
|
864
|
-
if (prompt.image) {
|
|
865
|
-
const userMessageImageCount = await (await getLastUserMessage()).getByTestId("user-message-image").count();
|
|
866
|
-
expect(userMessageImageCount).toBe(prompt.image > 3 ? 3 : prompt.image);
|
|
867
|
-
} else if (prompt.mix?.image) {
|
|
868
|
-
const userMessageImageCount = await (await getLastUserMessage()).getByTestId("user-message-image").count();
|
|
869
|
-
expect(userMessageImageCount).toBe(
|
|
870
|
-
prompt.mix.image > 3 ? 3 : prompt.mix.image
|
|
871
|
-
);
|
|
872
|
-
} else if (prompt.video) {
|
|
873
|
-
const userMessageVideoCount = await (await getLastUserMessage()).getByTestId("user-message-video").count();
|
|
874
|
-
expect(userMessageVideoCount).toBe(prompt.video > 3 ? 3 : prompt.video);
|
|
875
|
-
} else if (prompt.mix?.video) {
|
|
876
|
-
const userMessageVideoCount = (await getLastUserMessage()).getByTestId("user-message-video").count();
|
|
877
|
-
expect(userMessageVideoCount).toBe(
|
|
878
|
-
prompt.mix.video > 3 ? 3 : prompt.mix.video
|
|
879
|
-
);
|
|
880
|
-
} else if (prompt.audio) {
|
|
881
|
-
const userMessageAudioCount = await (await getLastUserMessage()).getByTestId("user-message-audio").count();
|
|
882
|
-
expect(userMessageAudioCount).toBe(prompt.audio > 3 ? 3 : prompt.audio);
|
|
883
|
-
} else if (prompt.mix?.audio) {
|
|
884
|
-
const userMessageAudioCount = (await getLastUserMessage()).getByTestId("user-message-audio").count();
|
|
885
|
-
expect(userMessageAudioCount).toBe(
|
|
886
|
-
prompt.mix.audio > 3 ? 3 : prompt.mix.audio
|
|
887
|
-
);
|
|
888
|
-
} else if (prompt.pdf) {
|
|
889
|
-
const userMessagePdfCount = await (await getLastUserMessage()).getByTestId("user-message-pdf").count();
|
|
890
|
-
expect(userMessagePdfCount).toBe(prompt.pdf > 3 ? 3 : prompt.pdf);
|
|
891
|
-
} else if (prompt.mix?.pdf) {
|
|
892
|
-
const userMessagePdfCount = await (await getLastUserMessage()).getByTestId("user-message-pdf").count();
|
|
893
|
-
expect(userMessagePdfCount).toBe(prompt.mix.pdf > 3 ? 3 : prompt.mix.pdf);
|
|
894
|
-
}
|
|
895
|
-
if (prompt.webSearch) {
|
|
896
|
-
const webSearchResults = (await getLastAgentMessage()).getByTestId(
|
|
897
|
-
"web-search-results"
|
|
898
|
-
);
|
|
899
|
-
await expect(webSearchResults).toBeVisible({
|
|
900
|
-
timeout: prompt.agentMessageTimeout || agentMessageTimeout
|
|
901
|
-
});
|
|
902
|
-
const webSearchResult = webSearchResults.getByTestId("web-search-result");
|
|
903
|
-
expect(await webSearchResult.count()).toBe(4);
|
|
904
|
-
}
|
|
905
|
-
await wait(1e3);
|
|
906
|
-
const threadUrl = page.url();
|
|
907
|
-
const threadId2 = threadUrl.split("/threads/")[1]?.split("?")[0];
|
|
908
|
-
expect(threadId2).toBeTruthy();
|
|
909
|
-
console.log("Thread:", threadId2);
|
|
910
|
-
const likeButton = (await getLastAgentMessage()).locator(
|
|
911
|
-
"[data-testid=like-button]"
|
|
912
|
-
);
|
|
913
|
-
if (prompts.indexOf(prompt) === 0 && artifacts) {
|
|
914
|
-
const dataTestId = threadId2 ? "chat" : "instruction";
|
|
915
|
-
let artifactsButton2 = page.getByTestId(
|
|
916
|
-
`${dataTestId}-instruction-artifacts-button`
|
|
917
|
-
);
|
|
918
|
-
await artifactsButton2.click();
|
|
919
|
-
const instructionModal2 = page.getByTestId(
|
|
920
|
-
`${dataTestId}-instruction-modal`
|
|
921
|
-
);
|
|
922
|
-
await expect(instructionModal2).toBeVisible();
|
|
923
|
-
const filePreviewClears = page.getByTestId(
|
|
924
|
-
`${dataTestId}-instruction-file-preview-clear`
|
|
925
|
-
);
|
|
926
|
-
let count = (artifacts.pdf || 0) + (artifacts.paste || 0);
|
|
927
|
-
if (count > 5) {
|
|
928
|
-
count = 5;
|
|
929
|
-
}
|
|
930
|
-
for (let i = 0; i < count; i++) {
|
|
931
|
-
const filePreviewClear = filePreviewClears.nth(count - i - 1);
|
|
932
|
-
await expect(filePreviewClear).toBeVisible();
|
|
933
|
-
await filePreviewClear.click();
|
|
934
|
-
await page.waitForTimeout(1e3);
|
|
935
|
-
}
|
|
936
|
-
expect(await filePreviewClears.count()).toBe(0);
|
|
937
|
-
if (artifacts.paste) {
|
|
938
|
-
for (let i = 0; i < artifacts.paste; i++) {
|
|
939
|
-
await simulatePaste(
|
|
940
|
-
page,
|
|
941
|
-
faker.lorem.sentence({ min: 550, max: 750 })
|
|
942
|
-
);
|
|
943
|
-
}
|
|
944
|
-
}
|
|
945
|
-
if (artifacts.pdf) {
|
|
946
|
-
const fileChooserPromise = page.waitForEvent("filechooser");
|
|
947
|
-
await page.getByTestId(`${dataTestId}-instruction-artifacts-upload-button`).click();
|
|
948
|
-
const testUsedPaths = Array.from({ length: artifacts.pdf }, (_, i) => {
|
|
949
|
-
const fileType = "pdf";
|
|
950
|
-
const fileName = `test${capitalizeFirstLetter(fileType)}${i + 1}`;
|
|
951
|
-
const extension = "pdf";
|
|
952
|
-
return path.join(
|
|
953
|
-
process2.cwd(),
|
|
954
|
-
"tests/shared",
|
|
955
|
-
fileType,
|
|
956
|
-
`${fileName}.${extension}`
|
|
957
|
-
);
|
|
958
|
-
});
|
|
959
|
-
const fileChooser = await fileChooserPromise;
|
|
960
|
-
await fileChooser.setFiles(testUsedPaths);
|
|
961
|
-
}
|
|
962
|
-
if ((artifacts.pdf || 0) + (artifacts.paste || 0) > 5) {
|
|
963
|
-
await expect(page.getByText("Maximum 5 files allowed")).toBeVisible();
|
|
964
|
-
}
|
|
965
|
-
const modalSaveButton = page.getByTestId(
|
|
966
|
-
`${dataTestId}-instruction-modal-save-button`
|
|
967
|
-
);
|
|
968
|
-
await expect(modalSaveButton).toBeVisible();
|
|
969
|
-
await modalSaveButton.click();
|
|
970
|
-
await wait(1e4);
|
|
971
|
-
const modalCloseButton = page.getByTestId(
|
|
972
|
-
`${dataTestId}-instruction-modal-close-button`
|
|
973
|
-
);
|
|
974
|
-
await expect(modalCloseButton).toBeVisible();
|
|
975
|
-
await modalCloseButton.click();
|
|
976
|
-
}
|
|
977
|
-
if (!prompt.stop) {
|
|
978
|
-
await expect(likeButton).toBeVisible({
|
|
979
|
-
timeout: prompt.agentMessageTimeout || agentMessageTimeout
|
|
980
|
-
});
|
|
981
|
-
const dislikeButton = (await getLastAgentMessage()).locator(
|
|
982
|
-
"[data-testid=dislike-button]"
|
|
983
|
-
);
|
|
984
|
-
await expect(dislikeButton).toBeVisible({
|
|
985
|
-
timeout: prompt.agentMessageTimeout || agentMessageTimeout
|
|
986
|
-
});
|
|
987
|
-
const getFilterLikedButton = ({ liked }) => page.getByTestId(`${liked ? "unfilter" : "filter"}-liked-button`);
|
|
988
|
-
await expect(getFilterLikedButton({ liked: false })).toBeVisible({
|
|
989
|
-
timeout: 1e4
|
|
990
|
-
});
|
|
991
|
-
if (prompt.like) {
|
|
992
|
-
await getFilterLikedButton({ liked: false }).click();
|
|
993
|
-
await expect(await getLastAgentMessage()).not.toBeVisible({
|
|
994
|
-
timeout: 8e3
|
|
995
|
-
});
|
|
996
|
-
await getFilterLikedButton({ liked: true }).click();
|
|
997
|
-
await expect(await getLastAgentMessage()).toBeVisible({
|
|
998
|
-
timeout: 8e3
|
|
999
|
-
});
|
|
1000
|
-
await likeButton.click();
|
|
1001
|
-
await wait(4e3);
|
|
1002
|
-
await getFilterLikedButton({ liked: false }).click();
|
|
1003
|
-
const unlikeButton = (await getLastAgentMessage()).locator(
|
|
1004
|
-
"[data-testid=unlike-button]"
|
|
1005
|
-
);
|
|
1006
|
-
await expect(unlikeButton).toBeVisible({
|
|
1007
|
-
timeout: 8e3
|
|
1008
|
-
});
|
|
1009
|
-
await unlikeButton.click();
|
|
1010
|
-
await expect(await getLastAgentMessage()).not.toBeVisible({
|
|
1011
|
-
timeout: 8e3
|
|
1012
|
-
});
|
|
1013
|
-
await getFilterLikedButton({ liked: true }).click();
|
|
1014
|
-
await expect(await getLastAgentMessage()).toBeVisible({
|
|
1015
|
-
timeout: 8e3
|
|
1016
|
-
});
|
|
1017
|
-
await getFilterLikedButton({ liked: false }).click();
|
|
1018
|
-
await expect(await getLastAgentMessage()).not.toBeVisible({
|
|
1019
|
-
timeout: 8e3
|
|
1020
|
-
});
|
|
1021
|
-
await getFilterLikedButton({ liked: true }).click();
|
|
1022
|
-
await wait(4e3);
|
|
1023
|
-
}
|
|
1024
|
-
if (prompt.model) {
|
|
1025
|
-
credits -= getModelCredits(prompt.model);
|
|
1026
|
-
if (prompt.debateAgent) {
|
|
1027
|
-
credits -= getModelCredits(prompt.debateAgent);
|
|
1028
|
-
}
|
|
1029
|
-
}
|
|
1030
|
-
page.getByTestId("hourly-limit-info");
|
|
1031
|
-
if (hourlyLimit - hourlyUsage === 0) {
|
|
1032
|
-
willFail = true;
|
|
1033
|
-
return;
|
|
1034
|
-
}
|
|
1035
|
-
const hourlyUsageLeft = await getHourlyUsageLeft();
|
|
1036
|
-
expect(hourlyUsageLeft).toBe((hourlyLimit - hourlyUsage).toString());
|
|
1037
|
-
const creditsLeft = await getCreditsLeft();
|
|
1038
|
-
if (creditsLeft !== null) {
|
|
1039
|
-
expect(creditsLeft).toBe(credits.toString());
|
|
1040
|
-
console.log(
|
|
1041
|
-
`\u2705 Credits assertion: ${creditsLeft} left (expected: ${credits})`
|
|
1042
|
-
);
|
|
1043
|
-
}
|
|
1044
|
-
if (prompt.model === "flux") {
|
|
1045
|
-
const imageGenerationButton = page.getByTestId(
|
|
1046
|
-
"image-generation-button"
|
|
1047
|
-
);
|
|
1048
|
-
await imageGenerationButton.click();
|
|
1049
|
-
await expect.poll(getAgentName, { timeout: 5e3 }).not.toBe("flux");
|
|
1050
|
-
const expectedDefaultAgent = !isMember ? "deepSeek" : "chatGPT";
|
|
1051
|
-
expect(await getAgentName()).toBe(expectedDefaultAgent);
|
|
1052
|
-
await imageGenerationButton.click();
|
|
1053
|
-
await expect.poll(getAgentName, { timeout: 5e3 }).toBe("flux");
|
|
1054
|
-
await imageGenerationButton.click();
|
|
1055
|
-
await page.waitForTimeout(2e3);
|
|
1056
|
-
expect(await getAgentName()).toBe(!isMember ? "deepSeek" : "chatGPT");
|
|
1057
|
-
}
|
|
1058
|
-
}
|
|
1059
|
-
if (prompt.delete) {
|
|
1060
|
-
await deleteMessageButton.click();
|
|
1061
|
-
await wait(200);
|
|
1062
|
-
await deleteMessageButton.click();
|
|
1063
|
-
await wait(4e3);
|
|
1064
|
-
await expect(deleteMessageButton).not.toBeVisible();
|
|
1065
|
-
}
|
|
1066
|
-
}
|
|
1067
|
-
const getNthMenuThread = async (nth) => {
|
|
1068
|
-
const threads = page.getByTestId("menu-thread-item");
|
|
1069
|
-
await threads.count();
|
|
1070
|
-
return threads.nth(nth);
|
|
1071
|
-
};
|
|
1072
|
-
const getFirstMenuThread = async () => {
|
|
1073
|
-
return getNthMenuThread(0);
|
|
1074
|
-
};
|
|
1075
|
-
if (bookmark) {
|
|
1076
|
-
(await getFirstMenuThread()).hover();
|
|
1077
|
-
const bookmarkButton = page.getByTestId("thread-not-bookmarked");
|
|
1078
|
-
await expect(bookmarkButton).toBeVisible();
|
|
1079
|
-
await bookmarkButton.click();
|
|
1080
|
-
const menuBookmarked = page.getByTestId("menu-bookmarked");
|
|
1081
|
-
await expect(menuBookmarked).toBeVisible({
|
|
1082
|
-
timeout: 1e4
|
|
1083
|
-
});
|
|
1084
|
-
await menuBookmarked.click();
|
|
1085
|
-
const threadNotBookmarked = page.getByTestId("thread-not-bookmarked");
|
|
1086
|
-
await expect(threadNotBookmarked).toBeVisible({
|
|
1087
|
-
timeout: 1e4
|
|
1088
|
-
});
|
|
1089
|
-
(await getFirstMenuThread()).hover();
|
|
1090
|
-
const menuNotBookmarked = page.getByTestId("menu-not-bookmarked");
|
|
1091
|
-
await expect(menuNotBookmarked).toBeVisible();
|
|
1092
|
-
await threadNotBookmarked.click();
|
|
1093
|
-
await wait(2e3);
|
|
1094
|
-
}
|
|
1095
|
-
if (isNewChat) {
|
|
1096
|
-
await page.getByTestId("new-chat-button").click();
|
|
1097
|
-
await wait(5e3);
|
|
1098
|
-
await expect(
|
|
1099
|
-
isMember ? page.getByTestId("user-message") : page.getByTestId("guest-message")
|
|
1100
|
-
).not.toBeVisible({
|
|
1101
|
-
timeout: 5e3
|
|
1102
|
-
});
|
|
1103
|
-
}
|
|
1104
|
-
};
|
|
1105
|
-
var signIn = async ({
|
|
1106
|
-
page,
|
|
1107
|
-
isOpened = false,
|
|
1108
|
-
signOut = false,
|
|
1109
|
-
register = false,
|
|
1110
|
-
email = process.env.VEX_TEST_EMAIL_2,
|
|
1111
|
-
password = process.env.VEX_TEST_PASSWORD_2
|
|
1112
|
-
}) => {
|
|
1113
|
-
const signInButton = page.getByTestId("login-button");
|
|
1114
|
-
if (!isOpened) {
|
|
1115
|
-
await expect(signInButton).toBeVisible({
|
|
1116
|
-
timeout: 15e3
|
|
1117
|
-
});
|
|
1118
|
-
await signInButton.click();
|
|
1119
|
-
}
|
|
1120
|
-
page.url().includes("extension");
|
|
1121
|
-
const modal = page.getByTestId("sign-in-modal");
|
|
1122
|
-
await expect(modal).toBeVisible();
|
|
1123
|
-
const emailInput = page.getByTestId("sign-in-email");
|
|
1124
|
-
await expect(emailInput).toBeVisible();
|
|
1125
|
-
await emailInput.fill(email);
|
|
1126
|
-
const passwordInput = page.getByTestId("sign-in-password");
|
|
1127
|
-
await expect(passwordInput).toBeVisible();
|
|
1128
|
-
await passwordInput.fill(password);
|
|
1129
|
-
await wait(2e3);
|
|
1130
|
-
const signInSubmit = page.getByTestId("login-submit");
|
|
1131
|
-
await expect(signInSubmit).toBeVisible();
|
|
1132
|
-
await signInSubmit.click({
|
|
1133
|
-
force: true
|
|
1134
|
-
});
|
|
1135
|
-
if (!!process.env.CI) {
|
|
1136
|
-
await page.waitForFunction(
|
|
1137
|
-
() => {
|
|
1138
|
-
const submitButton = document.querySelector(
|
|
1139
|
-
'[data-testid="login-submit"]'
|
|
1140
|
-
);
|
|
1141
|
-
return submitButton && submitButton.hasAttribute("data-redirect-url");
|
|
1142
|
-
},
|
|
1143
|
-
{ timeout: 15e3 }
|
|
1144
|
-
);
|
|
1145
|
-
const redirectUrl = await signInSubmit.getAttribute("data-redirect-url");
|
|
1146
|
-
if (!redirectUrl) {
|
|
1147
|
-
throw new Error("Redirect URL not found");
|
|
1148
|
-
}
|
|
1149
|
-
await page.goto(redirectUrl);
|
|
1150
|
-
}
|
|
1151
|
-
await wait(4e3);
|
|
1152
|
-
await expect(signInButton).not.toBeVisible();
|
|
1153
|
-
const accountButton = page.getByTestId("account-button");
|
|
1154
|
-
await expect(accountButton).toBeVisible();
|
|
1155
|
-
if (signOut) {
|
|
1156
|
-
await accountButton.click();
|
|
1157
|
-
const email2 = page.getByTestId("account-email");
|
|
1158
|
-
await expect(email2).toBeVisible();
|
|
1159
|
-
const logoutButton = page.getByTestId("account-logout-button");
|
|
1160
|
-
await expect(logoutButton).toBeVisible();
|
|
1161
|
-
await logoutButton.click();
|
|
1162
|
-
await expect(signInButton).toBeVisible({
|
|
1163
|
-
timeout: 15e3
|
|
1164
|
-
});
|
|
1165
|
-
}
|
|
1166
|
-
};
|
|
1167
|
-
|
|
1168
|
-
// src/collaboration.ts
|
|
1169
|
-
async function collaboration({
|
|
1170
|
-
page,
|
|
1171
|
-
isLive = false,
|
|
1172
|
-
isMember = false,
|
|
1173
|
-
browser,
|
|
1174
|
-
withShareLink = true,
|
|
1175
|
-
fingerprint,
|
|
1176
|
-
collaborate = "feedbackwallet@gmail.com"
|
|
1177
|
-
}) {
|
|
1178
|
-
const TEST_URL2 = getURL({
|
|
1179
|
-
fingerprint,
|
|
1180
|
-
isLive,
|
|
1181
|
-
isMember
|
|
1182
|
-
});
|
|
1183
|
-
const getMemberUrl = (path2) => getURL({
|
|
1184
|
-
isLive,
|
|
1185
|
-
isMember: true,
|
|
1186
|
-
path: path2
|
|
1187
|
-
});
|
|
1188
|
-
const context1 = await browser.newContext();
|
|
1189
|
-
const page1 = page;
|
|
1190
|
-
await page1.goto(TEST_URL2, { waitUntil: "networkidle" });
|
|
1191
|
-
await chat({
|
|
1192
|
-
bookmark: false,
|
|
1193
|
-
page: page1,
|
|
1194
|
-
isNewChat: false,
|
|
1195
|
-
isMember,
|
|
1196
|
-
instruction: "Let's plan a trip together",
|
|
1197
|
-
prompts: [
|
|
1198
|
-
{
|
|
1199
|
-
text: "I want to visit Japan. What should I know?",
|
|
1200
|
-
model: "deepSeek"
|
|
1201
|
-
}
|
|
1202
|
-
]
|
|
1203
|
-
});
|
|
1204
|
-
await page1.waitForTimeout(2e3);
|
|
1205
|
-
const threadUrl = page1.url();
|
|
1206
|
-
const threadId = threadUrl.split("/threads/")[1]?.split("?")[0];
|
|
1207
|
-
expect(threadId).toBeTruthy();
|
|
1208
|
-
console.log("Thread:", threadId);
|
|
1209
|
-
const threadShareButton = page1.getByTestId("thread-share-button");
|
|
1210
|
-
expect(threadShareButton).toBeVisible();
|
|
1211
|
-
const chatShareButton = page1.getByTestId("chat-share-button");
|
|
1212
|
-
await chatShareButton.click();
|
|
1213
|
-
await wait(1e3);
|
|
1214
|
-
const chatCollaborateButton = page1.getByTestId("chat-collaborate-button");
|
|
1215
|
-
expect(chatCollaborateButton).toBeVisible();
|
|
1216
|
-
await chatCollaborateButton.click();
|
|
1217
|
-
await wait(1e3);
|
|
1218
|
-
const shareInput = page1.getByTestId("chat-share-input");
|
|
1219
|
-
await expect(shareInput).toHaveValue(threadUrl);
|
|
1220
|
-
const shareCopyButton = page1.getByTestId("chat-share-copy-button");
|
|
1221
|
-
expect(shareCopyButton).toBeVisible();
|
|
1222
|
-
await shareCopyButton.click();
|
|
1223
|
-
await wait(1e3);
|
|
1224
|
-
const collaborateInput = page1.getByTestId("chat-collaborate-input");
|
|
1225
|
-
expect(collaborateInput).toBeVisible();
|
|
1226
|
-
await collaborateInput.fill("iliyan@chrry.ai");
|
|
1227
|
-
const collaborateAddButton = page1.getByTestId("chat-collaborate-add-button");
|
|
1228
|
-
await collaborateAddButton.click();
|
|
1229
|
-
const collaborateName = page1.getByTestId("chat-collaborator-name");
|
|
1230
|
-
await expect(collaborateName).toBeVisible({
|
|
1231
|
-
timeout: 8e3
|
|
1232
|
-
});
|
|
1233
|
-
const collaborateEmail = page1.getByTestId("chat-collaborator-email");
|
|
1234
|
-
await expect(collaborateEmail).toBeVisible();
|
|
1235
|
-
const collaborateStatus = page1.getByTestId("chat-collaborator-status");
|
|
1236
|
-
await expect(collaborateStatus).toHaveText("pending");
|
|
1237
|
-
const collaboratorRevokeButton = page1.getByTestId(
|
|
1238
|
-
"chat-collaborator-revoke-button"
|
|
1239
|
-
);
|
|
1240
|
-
await expect(collaboratorRevokeButton).toBeVisible();
|
|
1241
|
-
await collaboratorRevokeButton.click();
|
|
1242
|
-
await wait(1e3);
|
|
1243
|
-
await collaboratorRevokeButton.click();
|
|
1244
|
-
await wait(1e3);
|
|
1245
|
-
await expect(collaborateName).not.toBeVisible({
|
|
1246
|
-
timeout: 8e3
|
|
1247
|
-
});
|
|
1248
|
-
await expect(collaborateEmail).not.toBeVisible();
|
|
1249
|
-
await collaborateInput.fill(collaborate);
|
|
1250
|
-
await collaborateAddButton.click();
|
|
1251
|
-
await expect(collaborateName).toBeVisible({
|
|
1252
|
-
timeout: 8e3
|
|
1253
|
-
});
|
|
1254
|
-
await expect(collaborateEmail).toBeVisible();
|
|
1255
|
-
await expect(collaborateStatus).toHaveText("pending");
|
|
1256
|
-
await page1.getByTestId("chat-share-modal-close-button").click();
|
|
1257
|
-
await wait(1e3);
|
|
1258
|
-
const chatInput1 = page1.getByTestId("chat-textarea");
|
|
1259
|
-
const context2 = await browser.newContext();
|
|
1260
|
-
const page2 = await context2.newPage();
|
|
1261
|
-
await page2.goto(getMemberUrl(), {
|
|
1262
|
-
waitUntil: "networkidle"
|
|
1263
|
-
});
|
|
1264
|
-
await signIn({ page: page2 });
|
|
1265
|
-
await page2.goto(
|
|
1266
|
-
withShareLink ? `${getMemberUrl(`/threads/${threadId}`)}` : getMemberUrl(),
|
|
1267
|
-
{
|
|
1268
|
-
waitUntil: "networkidle"
|
|
1269
|
-
}
|
|
1270
|
-
);
|
|
1271
|
-
const chatInput2 = page2.getByTestId("chat-textarea");
|
|
1272
|
-
await expect(chatInput2).toBeDisabled();
|
|
1273
|
-
const acceptCollaborationButton = page2.getByTestId(
|
|
1274
|
-
"chat-accept-collaboration"
|
|
1275
|
-
);
|
|
1276
|
-
expect(acceptCollaborationButton).toBeVisible();
|
|
1277
|
-
const rejectCollaborationButton = page2.getByTestId(
|
|
1278
|
-
"chat-reject-collaboration"
|
|
1279
|
-
);
|
|
1280
|
-
expect(rejectCollaborationButton).toBeVisible();
|
|
1281
|
-
await acceptCollaborationButton.click();
|
|
1282
|
-
await expect(chatInput2).toBeEnabled({
|
|
1283
|
-
timeout: 8e3
|
|
1284
|
-
});
|
|
1285
|
-
await chat({
|
|
1286
|
-
page: page2,
|
|
1287
|
-
isNewChat: false,
|
|
1288
|
-
threadId,
|
|
1289
|
-
isMember: true,
|
|
1290
|
-
// Member user (signed in)
|
|
1291
|
-
prompts: [
|
|
1292
|
-
{
|
|
1293
|
-
text: "I've been to Tokyo before! The cherry blossoms are amazing in spring.",
|
|
1294
|
-
model: "deepSeek"
|
|
1295
|
-
}
|
|
1296
|
-
]
|
|
1297
|
-
});
|
|
1298
|
-
await page1.bringToFront();
|
|
1299
|
-
await page1.waitForTimeout(3e3);
|
|
1300
|
-
const messages1 = page1.getByTestId("message");
|
|
1301
|
-
const count1 = await messages1.count();
|
|
1302
|
-
expect(count1).toBeGreaterThanOrEqual(3);
|
|
1303
|
-
await chat({
|
|
1304
|
-
page: page1,
|
|
1305
|
-
isNewChat: false,
|
|
1306
|
-
threadId,
|
|
1307
|
-
isMember,
|
|
1308
|
-
creditsConsumed: 1,
|
|
1309
|
-
prompts: [
|
|
1310
|
-
{
|
|
1311
|
-
text: "That's great! When is the best time to see cherry blossoms?",
|
|
1312
|
-
model: "deepSeek"
|
|
1313
|
-
}
|
|
1314
|
-
]
|
|
1315
|
-
});
|
|
1316
|
-
await page2.bringToFront();
|
|
1317
|
-
await page2.waitForTimeout(3e3);
|
|
1318
|
-
const messages2 = page2.getByTestId("message");
|
|
1319
|
-
const count2 = await messages2.count();
|
|
1320
|
-
expect(count2).toBeGreaterThanOrEqual(5);
|
|
1321
|
-
await page1.bringToFront();
|
|
1322
|
-
await chatInput1.click();
|
|
1323
|
-
await chatInput1.fill("I'm typing...");
|
|
1324
|
-
await page2.bringToFront();
|
|
1325
|
-
await page2.waitForTimeout(2e3);
|
|
1326
|
-
expect(
|
|
1327
|
-
await page2.getByTestId("typing-indicator").count()
|
|
1328
|
-
).toBeGreaterThanOrEqual(1);
|
|
1329
|
-
await page2.waitForTimeout(5e3);
|
|
1330
|
-
expect(await page2.getByTestId("typing-indicator").count()).toBe(0);
|
|
1331
|
-
await chatInput2.click();
|
|
1332
|
-
await chatInput2.fill("I'm typing too...");
|
|
1333
|
-
await page1.bringToFront();
|
|
1334
|
-
await page1.waitForTimeout(2e3);
|
|
1335
|
-
expect(
|
|
1336
|
-
await page1.getByTestId("typing-indicator").count()
|
|
1337
|
-
).toBeGreaterThanOrEqual(1);
|
|
1338
|
-
await page1.waitForTimeout(3e3);
|
|
1339
|
-
expect(await page1.getByTestId("typing-indicator").count()).toBe(0);
|
|
1340
|
-
await context1.close();
|
|
1341
|
-
await context2.close();
|
|
1342
|
-
}
|
|
1343
|
-
var limit = async ({
|
|
1344
|
-
page,
|
|
1345
|
-
isMember,
|
|
1346
|
-
isSubscriber
|
|
1347
|
-
}) => {
|
|
1348
|
-
const hourlyLimit = isSubscriber ? 100 : isMember ? 30 : 10;
|
|
1349
|
-
console.log(
|
|
1350
|
-
`\u{1F3AF} Testing hourly limit: ${hourlyLimit} requests for ${isMember ? "member" : "guest"}`
|
|
1351
|
-
);
|
|
1352
|
-
const limitPrompts = Array.from({ length: hourlyLimit }, (_, i) => {
|
|
1353
|
-
const isFluxMessage = i % (isMember ? 5 : 3) === 0;
|
|
1354
|
-
const isClaudeMessage = isMember && i % 5 === 0;
|
|
1355
|
-
const isChatGPTMessage = isMember && i % 3 === 0;
|
|
1356
|
-
const isWebSearch = (isClaudeMessage || isChatGPTMessage) && !isFluxMessage && i % 2 === 0;
|
|
1357
|
-
const like = isWebSearch || isFluxMessage ? true : false;
|
|
1358
|
-
return {
|
|
1359
|
-
text: isFluxMessage ? `Create a beautiful ${faker.color.human()} ${faker.animal.type()} in a ${faker.location.city()} setting, digital art style` : i === hourlyLimit ? `Find latest news about ${faker.company.name()}` : `Test message ${i + 1} - ${faker.lorem.sentence()}`,
|
|
1360
|
-
model: isFluxMessage ? "flux" : isClaudeMessage ? "claude" : isChatGPTMessage ? "chatGPT" : "deepSeek",
|
|
1361
|
-
agentMessageTimeout: isFluxMessage ? 6e4 : 3e4,
|
|
1362
|
-
// Flux needs more time
|
|
1363
|
-
webSearch: isWebSearch,
|
|
1364
|
-
shouldFail: i === hourlyLimit,
|
|
1365
|
-
// Only fail on last message
|
|
1366
|
-
like
|
|
1367
|
-
};
|
|
1368
|
-
});
|
|
1369
|
-
const failPrompt = {
|
|
1370
|
-
text: "This message should fail due to hourly limit",
|
|
1371
|
-
model: "deepSeek",
|
|
1372
|
-
agentMessageTimeout: 3e4,
|
|
1373
|
-
shouldFail: true,
|
|
1374
|
-
// Flag to indicate this should fail
|
|
1375
|
-
webSearch: true
|
|
1376
|
-
// Test web search on the failing request too
|
|
1377
|
-
};
|
|
1378
|
-
await chat({
|
|
1379
|
-
isNewChat: true,
|
|
1380
|
-
page,
|
|
1381
|
-
isMember,
|
|
1382
|
-
instruction: `Testing hourly limit of ${hourlyLimit} requests`,
|
|
1383
|
-
prompts: [...limitPrompts, failPrompt]
|
|
1384
|
-
});
|
|
1385
|
-
};
|
|
1386
|
-
var thread = async ({
|
|
1387
|
-
page,
|
|
1388
|
-
isMember,
|
|
1389
|
-
bookmark,
|
|
1390
|
-
createChat = true
|
|
1391
|
-
}) => {
|
|
1392
|
-
createChat && await chat({
|
|
1393
|
-
bookmark,
|
|
1394
|
-
isNewChat: true,
|
|
1395
|
-
page,
|
|
1396
|
-
isMember,
|
|
1397
|
-
instruction: "Help me write a short story",
|
|
1398
|
-
prompts: Array.from({ length: 3 }, (_, i) => {
|
|
1399
|
-
return {
|
|
1400
|
-
text: `Test message ${i + 1} - ${faker.lorem.sentence()}`,
|
|
1401
|
-
model: "deepSeek",
|
|
1402
|
-
agentMessageTimeout: 3e4
|
|
1403
|
-
};
|
|
1404
|
-
})
|
|
1405
|
-
});
|
|
1406
|
-
const getNthThread = async (nth) => {
|
|
1407
|
-
const threads = page.getByTestId("threads-item");
|
|
1408
|
-
await threads.count();
|
|
1409
|
-
return threads.nth(nth);
|
|
1410
|
-
};
|
|
1411
|
-
const getFirstThread = async () => {
|
|
1412
|
-
return getNthThread(0);
|
|
1413
|
-
};
|
|
1414
|
-
const getSecondThread = async () => {
|
|
1415
|
-
return getNthThread(1);
|
|
1416
|
-
};
|
|
1417
|
-
const threadsContainer = page.getByTestId("threads-container");
|
|
1418
|
-
const loadMore = page.getByTestId("load-more-threads-menu");
|
|
1419
|
-
if (createChat) {
|
|
1420
|
-
await expect(loadMore).toBeVisible();
|
|
1421
|
-
await loadMore.click();
|
|
1422
|
-
await wait(5e3);
|
|
1423
|
-
}
|
|
1424
|
-
await expect(
|
|
1425
|
-
(await getFirstThread()).getByTestId("threads-bookmarked")
|
|
1426
|
-
).toBeVisible({
|
|
1427
|
-
timeout: 15e3
|
|
1428
|
-
});
|
|
1429
|
-
await expect(
|
|
1430
|
-
(await getFirstThread()).getByTestId("threads-not-bookmarked")
|
|
1431
|
-
).not.toBeVisible({
|
|
1432
|
-
timeout: 15e3
|
|
1433
|
-
});
|
|
1434
|
-
const threadsCount = page.getByTestId("threads-item");
|
|
1435
|
-
const count = await threadsCount.count();
|
|
1436
|
-
createChat ? expect(count).toBe(1) : expect(count).toBe(2);
|
|
1437
|
-
await expect(threadsContainer).toBeVisible();
|
|
1438
|
-
const search = page.getByTestId("threads-search");
|
|
1439
|
-
await expect(search).toBeVisible();
|
|
1440
|
-
const threadsCollaboration = page.getByTestId("threads-collaboration");
|
|
1441
|
-
await expect(threadsCollaboration).toBeVisible();
|
|
1442
|
-
const threadsSortButtonDate = page.getByTestId("threads-sort-button-date");
|
|
1443
|
-
await expect(threadsSortButtonDate).toBeVisible();
|
|
1444
|
-
await threadsSortButtonDate.click();
|
|
1445
|
-
const threadsSortButton = page.getByTestId("threads-sort-button-star");
|
|
1446
|
-
await expect(threadsSortButton).toBeVisible();
|
|
1447
|
-
await threadsSortButton.click();
|
|
1448
|
-
const editThreadButton = (await getFirstThread()).getByTestId(
|
|
1449
|
-
"edit-thread-button"
|
|
1450
|
-
);
|
|
1451
|
-
await expect(editThreadButton).toBeVisible();
|
|
1452
|
-
await editThreadButton.click();
|
|
1453
|
-
const editThreadTextarea = page.getByTestId("edit-thread-textarea");
|
|
1454
|
-
await editThreadTextarea.fill("New thread title");
|
|
1455
|
-
const editThreadSaveButton = page.getByTestId("edit-thread-save-button");
|
|
1456
|
-
await expect(editThreadSaveButton).toBeVisible();
|
|
1457
|
-
await editThreadSaveButton.click();
|
|
1458
|
-
const threadTitle = threadsContainer.getByText("New thread title");
|
|
1459
|
-
await expect(threadTitle).toBeVisible();
|
|
1460
|
-
await editThreadButton.click();
|
|
1461
|
-
const editThreadGenerateTitleButton = page.getByTestId(
|
|
1462
|
-
"edit-thread-generate-title-button"
|
|
1463
|
-
);
|
|
1464
|
-
await expect(editThreadGenerateTitleButton).toBeVisible();
|
|
1465
|
-
await editThreadGenerateTitleButton.click();
|
|
1466
|
-
await wait(2e3);
|
|
1467
|
-
await editThreadSaveButton.click();
|
|
1468
|
-
await wait(2e3);
|
|
1469
|
-
await expect(threadTitle).not.toBeVisible();
|
|
1470
|
-
const threadTitleGenerated2 = (await getFirstThread()).getByTestId(
|
|
1471
|
-
"threads-item-title"
|
|
1472
|
-
);
|
|
1473
|
-
await expect(threadTitleGenerated2).toBeVisible();
|
|
1474
|
-
const newTitle = await threadTitleGenerated2.textContent();
|
|
1475
|
-
if (!newTitle) {
|
|
1476
|
-
throw new Error("Thread title not found");
|
|
1477
|
-
}
|
|
1478
|
-
await editThreadButton.click();
|
|
1479
|
-
const deleteThreadButton = page.getByTestId("delete-thread-button");
|
|
1480
|
-
await expect(deleteThreadButton).toBeVisible();
|
|
1481
|
-
await deleteThreadButton.click();
|
|
1482
|
-
await wait(1e3);
|
|
1483
|
-
await deleteThreadButton.click();
|
|
1484
|
-
await wait(3e3);
|
|
1485
|
-
await expect(threadsContainer).toBeVisible();
|
|
1486
|
-
await expect(page.getByText(newTitle)).not.toBeVisible();
|
|
1487
|
-
if (createChat) {
|
|
1488
|
-
await chat({
|
|
1489
|
-
isNewChat: true,
|
|
1490
|
-
page,
|
|
1491
|
-
isMember,
|
|
1492
|
-
instruction: "Help me write a short story",
|
|
1493
|
-
bookmark,
|
|
1494
|
-
prompts: Array.from({ length: 3 }, (_, i) => {
|
|
1495
|
-
return {
|
|
1496
|
-
text: `Test message ${i + 1} - ${faker.lorem.sentence()}`,
|
|
1497
|
-
model: "deepSeek",
|
|
1498
|
-
agentMessageTimeout: 3e4
|
|
1499
|
-
};
|
|
1500
|
-
})
|
|
1501
|
-
});
|
|
1502
|
-
const menuHomeButton = page.getByTestId("menu-home-button");
|
|
1503
|
-
await expect(menuHomeButton).toBeVisible();
|
|
1504
|
-
await menuHomeButton.click();
|
|
1505
|
-
await wait(3e3);
|
|
1506
|
-
await chat({
|
|
1507
|
-
isNewChat: false,
|
|
1508
|
-
creditsConsumed: 3,
|
|
1509
|
-
bookmark: false,
|
|
1510
|
-
page,
|
|
1511
|
-
isMember,
|
|
1512
|
-
instruction: "Help me write a short story",
|
|
1513
|
-
prompts: Array.from({ length: 3 }, (_, i) => {
|
|
1514
|
-
return {
|
|
1515
|
-
text: `Test message ${i + 1} - ${faker.lorem.sentence()}`,
|
|
1516
|
-
model: "deepSeek",
|
|
1517
|
-
agentMessageTimeout: 3e4
|
|
1518
|
-
};
|
|
1519
|
-
})
|
|
1520
|
-
});
|
|
1521
|
-
await loadMore.click();
|
|
1522
|
-
await wait(1e3);
|
|
1523
|
-
await expect(
|
|
1524
|
-
(await getFirstThread()).getByTestId("threads-bookmarked")
|
|
1525
|
-
).not.toBeVisible();
|
|
1526
|
-
await (await getFirstThread()).getByTestId("threads-not-bookmarked").click();
|
|
1527
|
-
await wait(1e3);
|
|
1528
|
-
await expect(
|
|
1529
|
-
(await getSecondThread()).getByTestId("threads-bookmarked")
|
|
1530
|
-
).toBeVisible();
|
|
1531
|
-
await expect(
|
|
1532
|
-
(await getSecondThread()).getByTestId("threads-not-bookmarked")
|
|
1533
|
-
).not.toBeVisible();
|
|
1534
|
-
await thread({
|
|
1535
|
-
page,
|
|
1536
|
-
isMember,
|
|
1537
|
-
createChat: false
|
|
1538
|
-
});
|
|
1539
|
-
}
|
|
1540
|
-
};
|
|
1541
80
|
|
|
1542
|
-
export { LIVE_URL, TEST_GUEST_FINGERPRINTS, TEST_MEMBER_EMAILS, TEST_MEMBER_FINGERPRINTS, TEST_URL, VEX_TEST_EMAIL, VEX_TEST_EMAIL_2, VEX_TEST_EMAIL_3, VEX_TEST_FINGERPRINT, VEX_TEST_FINGERPRINT_2, VEX_TEST_FINGERPRINT_3, VEX_TEST_PASSWORD, VEX_TEST_PASSWORD_2, VEX_TEST_PASSWORD_3, capitalizeFirstLetter,
|
|
81
|
+
export { LIVE_URL, TEST_GUEST_FINGERPRINTS, TEST_MEMBER_EMAILS, TEST_MEMBER_FINGERPRINTS, TEST_URL, VEX_TEST_EMAIL, VEX_TEST_EMAIL_2, VEX_TEST_EMAIL_3, VEX_TEST_FINGERPRINT, VEX_TEST_FINGERPRINT_2, VEX_TEST_FINGERPRINT_3, VEX_TEST_PASSWORD, VEX_TEST_PASSWORD_2, VEX_TEST_PASSWORD_3, capitalizeFirstLetter, getURL, isCI, simulateInputPaste, simulatePaste, wait };
|
|
1543
82
|
//# sourceMappingURL=index.mjs.map
|
|
1544
83
|
//# sourceMappingURL=index.mjs.map
|