Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

update test for feedback, comment, dataset, user #373

Open
wants to merge 11 commits into
base: main
Choose a base branch
from
Open
8 changes: 5 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -66,9 +66,11 @@ With the hosted version:
2. Setup a PostgreSQL instance (version 15 minimum)
3. Copy the content of `packages/backend/.env.example` to `packages/backend/.env` and fill the missing values
4. Copy the content of `packages/frontend/.env.example` to `packages/backend/.env`
5. Run `npm install`
6. Run `npm run migrate:db`
7. Run `npm run dev`
6. Run `npm install`
7. Run `npm run migrate:db`
8. Run `npm run dev`
8. Run `npm run test` for run test playwright
8. Run `npm run test:debug` for run test debug playwright

You can now open the dashboard at `http://localhost:8080`.
When using our JS or Python SDK, you need to set the environment variable `LUNARY_API_URL` to `http://localhost:3333`. You can use `LUNARY_VERBOSE=True` to see all the event sent by the SDK
Expand Down
227 changes: 227 additions & 0 deletions e2e/feebback.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,227 @@
import { Page, expect, test } from "@playwright/test"
require('dotenv').config();
import { config , UserInfo} from "./helpers/constants"
import { uniqueStr } from "./helpers/uniqueStr"
import lunary from "lunary"
import OpenAI from "openai"
import { monitorOpenAI } from "lunary/openai"
import { setOrgPro } from "./utils/db"
import { LoginPage } from "./page/login.po"
import { CommAction } from "./page/common.po"
import { HomePage } from "./page/home.po"
import { SignUpPage } from "./page/signUp.po"
import { AnalyticsPage } from "./page/analytics.po"
import { LogsPage } from "./page/logs.po"
import { ThreatsPage } from "./page/threats.po";
import { TracesPage } from "./page/traces.po";

let page: Page;
let context: any;
let userName:string;
let email :string;
let email1 :string;
let email2 :string;
let userName1 :string;
let userName2 :string;

let contentSystem1 :string;
let contentSystem2 :string;
let contentUser1 :string;
let contentUser2 :string;

test.describe('Feedback', () => {
test.beforeAll(async ({ browser }) => {
context = await browser.newContext();
page = await context.newPage();
const login = new LoginPage(page);

const homePage = new HomePage(page);
const signUpPage = new SignUpPage(page);
const commonPage = new CommAction(page);
const analyticsPage = new AnalyticsPage(page);

userName =uniqueStr('user');
email = uniqueStr('test') + '@example.com';

email1 = uniqueStr('test1') + '@example.com';
userName1 =uniqueStr('user1');

email2 = uniqueStr('test2') + '@example.com';
userName2 =uniqueStr('user2');

contentSystem1 = "Hi friend message 1";
contentSystem2 = "Hi friend message 2";
contentUser1 = "Can you help me on message 1";
contentUser2 = "Can you help me on message 2";
await login.openUrl(config.BASE_URL);
await homePage.clickSignUpBtn();
await signUpPage.signUpAccountStep1(email, UserInfo.password, userName);
await signUpPage.signUpAccountStep2("TESTPROJECT","TESTORG", UserInfo.companySize, UserInfo.option);
await signUpPage.clickSkipDashboard();
await commonPage.clickMenu('Analytics');
const projectId = await analyticsPage.getProjectId();
await commonPage.initLunaryOpenAI(projectId);
await setOrgPro()
const openai = monitorOpenAI(new OpenAI({ apiKey: config.OPENAI_API_KEY}))
const thread = lunary.openThread({
userId: "tristina Test",
userProps: { name: "tristina Testing" },
tags: ['testing thread']
})
const msgId = thread.trackMessage({
role: 'assistant',
content: 'testing'
})
const result = await openai.chat.completions.create({
model: "gpt-4o",
temperature: 0.9,
tags: ["chat", "support"], // Optional: tags
user: email1, // Optional: user ID
userProps: { name: userName1 }, // Optional: user properties
messages: [
{ role: "system", content: contentSystem1 },
{ role: "user", content: contentUser1 },
],

}).setParent(msgId)


const msgId2 = thread.trackMessage({
role: 'user',
content: result.choices[0].message.content
})

const result2 = await openai.chat.completions.create({
model: "gpt-4o",
temperature: 0.9,
tags: ["chat", "support"], // Optional: tags
user: email2, // Optional: user ID
userProps: { name: userName2 }, // Optional: user properties
messages: [
{ role: "system", content: contentSystem2},
{ role: "user", content: contentUser2},
],

}).setParent(msgId2)

const agent = lunary.wrapAgent(function ChatbotAgent(query) {
console.log('test agent');
})

await agent("Hello!").setParent(msgId)
const calculator = lunary.wrapTool(async function Calculator(input) {
// Your custom logic
// ...
})

await calculator('1 + 2')
});



test("Adding a thumb up/down to a from a llm call to verify feedback", async ({page}) => {
const commonPage = new CommAction(page);
const logsPage = new LogsPage(page);
const loginPage = new LoginPage(page);

await loginPage.openUrl(config.BASE_URL);
await loginPage.login(email, UserInfo.password);

await commonPage.clickMenu('Logs');

await logsPage.clickMessage(contentUser2);
await logsPage.verifyThumbUpDownIsDisplayedOnBanner();
await logsPage.clickThumbUpIcon();
await logsPage.verifyThumbUpIconTurnGreen();
await logsPage.closeModal();
await logsPage.verifyThumbUpIconIsDisplayed(contentUser2);

await logsPage.clickMessage(contentUser2);
await logsPage.clickThumbDownIcon();
await logsPage.verifyThumbDownIconTurnRed();
await logsPage.closeModal();
await logsPage.verifyThumbDownIconIsDisplayed(contentUser2);

})

test("Adding a comment and verify it", async ({page}) => {
const commonPage = new CommAction(page);
const logsPage = new LogsPage(page);
const loginPage = new LoginPage(page);

await loginPage.openUrl(config.BASE_URL);
await loginPage.login(email, UserInfo.password);

await commonPage.clickMenu('Logs');

await logsPage.clickMessage(contentUser2);
await logsPage.clickMessageIcon();
const comment =uniqueStr('user');
await logsPage.sendComment(comment);
await logsPage.closeModal();
await logsPage.hoverCommentIcon(contentUser2);
await logsPage.verifyCommentIsDisplayed(contentUser2, comment);
})

test("Adding a thumb up/down from a trace to verify feedback", async ({page}) => {
const commonPage = new CommAction(page);
const logsPage = new LogsPage(page);
const threatsPage = new ThreatsPage(page);
const tracesPage = new TracesPage(page);
const loginPage = new LoginPage(page);

await loginPage.openUrl(config.BASE_URL);
await loginPage.login(email, UserInfo.password);

await commonPage.clickMenu('Logs');
await commonPage.clickTab('Threads');
await threatsPage.clickTagName('testing thread');
await threatsPage.clickViewTraceButton();
await tracesPage.clickTagName('gpt-4o');
await tracesPage.verifyThumbUpDownIsDisplayedOnBanner();
await tracesPage.clickThumbUpIcon();

await tracesPage.verifyThumbUpIconTurnGreen();

await commonPage.clickMenu('Logs');
await logsPage.verifyThumbUpIconIsDisplayed(contentUser1);

await commonPage.clickTab('Threads');
await threatsPage.clickTagName('testing thread');
await threatsPage.clickViewTraceButton();
await tracesPage.clickTagName('gpt-4o');
await tracesPage.clickThumbDownIcon();
await tracesPage.verifyThumbDownIconTurnRed();

await commonPage.clickMenu('Logs');
await logsPage.verifyThumbDownIconIsDisplayed(contentUser1);


})

test("Adding a comment from a trace to verify feedback", async ({page}) => {
const commonPage = new CommAction(page);
const logsPage = new LogsPage(page);
const loginPage = new LoginPage(page);
const threatsPage = new ThreatsPage(page);
const tracesPage = new TracesPage(page);
const comment =uniqueStr('comment from trace');
await loginPage.openUrl(config.BASE_URL+'');
await loginPage.login(email, UserInfo.password);

await commonPage.clickMenu('Logs');

await commonPage.clickTab('Threads');
await threatsPage.clickTagName('testing thread');
await threatsPage.clickViewTraceButton();
await tracesPage.clickTagName('gpt-4o');
await tracesPage.clickMessageIcon();
await tracesPage.sendComment(comment);

await commonPage.clickMenu('Logs');
await logsPage.hoverCommentIcon(contentUser1);
await logsPage.verifyCommentIsDisplayed(contentUser1, comment);


})
});
26 changes: 26 additions & 0 deletions e2e/helpers/constants.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
const BASE_URL = process.env.APP_URL || 'http://localhost:8080';
const OPENAI_API_KEY = process.env.OPENAI_API_KEY;
const API_URL = process.env.LUNARY_API_URL || 'http://localhost:3333';
if (
!OPENAI_API_KEY
) {
throw 'Missing environment variables';
}
export const config = {
BASE_URL,
OPENAI_API_KEY,
API_URL,
};

export const Constants = {
defaultPassword: 'bl@ckr0ck',
defaultuserName: 'bl@[email protected]'
};

export const UserInfo = {
userName: 'Tristina',
email: '[email protected]',
password: '12345678',
companySize: '6-49',
option: 'Other',
};
29 changes: 29 additions & 0 deletions e2e/helpers/uniqueStr.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
export function generateCode(length: number) {
let result = '';
const characters = '0123456789';
const charactersLength = characters.length;
let counter = 0;
while (counter < length) {
result += characters.charAt(Math.floor(Math.random() * charactersLength));
counter += 1;
}
return result;
}

export function generateUserName(length: number) {
let result = '';
const characters = '0123456789';
const charactersLength = characters.length;
let counter = 0;
while (counter < length) {
result += characters.charAt(Math.floor(Math.random() * charactersLength));
counter += 1;
}
result = 'test'+result;
return result;
}

export function uniqueStr(s: string) {
const now = new Date().getTime();
return `${s}${now}`;
}
17 changes: 17 additions & 0 deletions e2e/page/analytics.po.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import { Locator, Page, expect } from '@playwright/test';
import { CommAction } from './common.po';

export class AnalyticsPage extends CommAction {
readonly page: Page;

constructor(page: Page) {
super(page);
this.page = page;
}

async getProjectId(): Promise<string> {
return await this.page.locator('//code').innerText();
}


}
Loading
Loading