-
Notifications
You must be signed in to change notification settings - Fork 60
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
feature: Evaluations playground #2 #132
Conversation
4b7f345
to
db027e1
Compare
}), | ||
{ type: 'json' }, | ||
) | ||
.handler(async ({ input, ctx }) => { | ||
const commitsScope = new CommitsRepository(ctx.project.workspaceId) | ||
const commit = await commitsScope | ||
.getCommitById(input.commitId) | ||
.getCommitByUuid({ uuid: input.commitUuid, project: ctx.project }) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nice
@@ -81,7 +81,7 @@ describe('destroyDocumentAction', async () => { | |||
it('fails when trying to remove a document from a merged commit', async () => { | |||
const [_, error] = await destroyDocumentAction({ | |||
projectId: project.id, | |||
commitId: merged.id, | |||
commitUuid: merged.uuid, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why this change?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
we are working with commit uuids in the frontend constantly, using it in actions saves us one roundtrip to get the commit id
db027e1
to
ad7ebac
Compare
@@ -28,13 +28,12 @@ export const addMessageHandler = factory.createHandlers( | |||
workspace, | |||
documentLogUuid, | |||
messages, | |||
providerLogHandler: (log) => { | |||
// TODO: Review why this is possibly undefined now | |||
queues.defaultQueue.jobs.enqueueCreateProviderLogJob!({ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this was wrong provider logs have to be saved in sync
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I understand but now the request takes longer. This is the tradeoff no?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yup
@@ -42,16 +43,17 @@ export const runHandler = factory.createHandlers( | |||
commit, | |||
parameters, | |||
providerLogHandler: (log) => { | |||
queues.defaultQueue.jobs.enqueueCreateProviderLogJob({ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ditto
ad7ebac
to
dea4ce5
Compare
}, | ||
}).then((r) => r.unwrap()) | ||
|
||
await pipeToStream(stream, result.stream) | ||
|
||
// TODO: review if this is needed and why it's not in addMessages handler? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@andresgutgon question for you ☝🏼
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Need what? Sorry I don't understand
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
queues.defaultQueue.jobs.enqueueCreateDocumentLogJob
this is being called here but it's not being called in the addMessages handler which also calls ai, I'm wondering if it should be removed from here or added to addMessages
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes because a document log is created when a document is run. But when a message is created only the logs for the AI are created (provider log)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
aaahm ok 👍🏼
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Remove this comment in the next PR
} | ||
|
||
return result | ||
}) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i've implemented a regular REST get operation with filters instead of custom action for each type of get, this means that getProviderLogsForDocumentLogAction 👇🏼 is no longer needed
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
cool
@@ -28,7 +28,7 @@ export async function addMessagesAction({ | |||
const sdk = await createSdk().then((r) => r.unwrap()) | |||
const stream = createStreamableValue<ChainEvent, Error>() | |||
|
|||
const response = sdk.addMessges({ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ultra typo please be careful this is public api
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sorry about that.
</div> | ||
</> | ||
) | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
very similar to document editor playground but not exactly the same. Probably some opportunities for DRYing but will evaluate later
@@ -61,7 +62,7 @@ export default function EvaluationEditor({ | |||
useEffect(() => { | |||
readMetadata({ | |||
prompt: value, | |||
withParameters: Object.keys(PARAMETERS_FROM_LOG), | |||
// withParameters: ['messages', 'response'], // TODO: uncomment this line once I understand why it breaks |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
using withParamaters fails with a "variable not declared", have to debug the compiler. For now just commenting out since everything works without it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
cc @csansoon you probably can provide some light here
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Unlike with documents, evaluations do not have the ability to create new variables just by referencing them in the code. Instead, it has a bunch of predefined variables, and users can only use those. This means that, to "readMetadata", the compiler must know which are these variables names so that it knows if it would fail when you reference a parameters. If it exists in that list nothing happens, but if it doesn't, it should fail with a "variable not declared".
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The variable is declared, just not assigned a value yet
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
well, if withParameters
contains messages
, that's a bug in the compiler then 😅
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
talked offline, will fix it in the next pr
@@ -50,6 +51,10 @@ export default class Transaction { | |||
* https://github.com/rails/rails/blob/main/activerecord/lib/active_record/connection_adapters/postgresql_adapter.rb#L769. | |||
*/ | |||
static toResultError(error: unknown): ErrorResult<Error> { | |||
if (env.NODE_ENV === 'development') { | |||
console.error(error) | |||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
make our lives easier
const result = await query | ||
|
||
return Result.ok(result) | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
pagination very needed here since we expect 10s of thousands of logs
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
hmm seems like very low level no? I don't want to reimplement the findAll query, just add some pagination to it
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What do you mean? Is the official way of doing pagination in drizzle
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
no not talking about drizzle's api saying that if i already have the find and findall methods implementing in repositories i don't want to call another method to have the same but paginated, i just wanna indicate pagination as an options of those methods.
I will use page and pageSize instead of limit and offset though, I think it makes more sense, will do in the next PR
} | ||
|
||
if (opts.offset !== undefined) { | ||
// @ts-expect-error |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
since this is an abstract class implementing operations over a query that is defined by the children classes typescript has difficulties understanding the types, adding a bit of technical debt here in favour of moving forward towards the MVP
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Check if this comment can help https://github.com/latitude-dev/latitude-llm/pull/132/files#r1744961217
const inputCost = (inputCostPer1MToken * (inputTokens ?? 0)) / 1_000_000 | ||
const outputCost = (outputCostPer1MToken * (outputTokens ?? 0)) / 1_000_000 | ||
const inputCost = | ||
(inputCostPer1MToken * (isNaN(inputTokens) ? 0 : inputTokens)) / 1_000_000 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this was a bug, vercel's ai can return NaN in some token usage for some providers. Probably a bug on their end but regardless we have to defend ourselves.
}: ModalProps) { | ||
return ( | ||
<Dialog open={open} defaultOpen={defaultOpen} onOpenChange={onOpenChange}> | ||
<DialogContent className='sm:max-w-modal'> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this class wasn't getting applied because DialogContent was doing nothing with the prop className
dea4ce5
to
6bd65c2
Compare
1c7dda6
to
bff38e0
Compare
useEffect(() => { | ||
if (!metadata) return | ||
|
||
// Remove only inputs that are no longer in the metadata, and add new ones | ||
// Leave existing inputs as they are | ||
setInputs( | ||
Object.fromEntries( | ||
Array.from(metadata.parameters).map((param) => { | ||
if (param in inputs) return [param, inputs[param]!] | ||
|
||
return [param, { value: '', type: 'input' }] | ||
}), | ||
), | ||
) | ||
}, [metadata]) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There cannot be "new inputs". Evaluation only have the default predefined parameters that are extracted from a log.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
hmm weird ux imo, I'd rather show them a message telling them they have to include the messages variable if it's not present in the document, rather than showing an input for a variable that they have removed from the document
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, but the parameters always exist, wether you use them in the prompt or not. It is not like Documents, where ONLY when you reference a variable in the code a new parameter is created. In this case, users must only reference variables from a list of predefined variables, which are filled with data automatically from logs. I think we should always display this list to the user, so they’re aware of the parameters they have access to, even if they’re not currently using them in their code.
(resending this message, this was removed by accident)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
but if they don't use it in the document they won't have an effect at all when you run the prompt no? it's just weird to have an input for a variable that won't have any usage in the document. I understand that internally they exist in the state of the compiler when running the document, but that's not relevant to the user. It's better to tell the user "hey, remember to add the messages variable to your document" rather than just showing an input that has no effect on the evaluation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe we shouldn't display it as a bunch of inputs. We could just display a "log" there, with the ability to modify it.
f9bf84c
to
34f1c7e
Compare
...evaluations/[evaluationUuid]/editor/_components/EvaluationEditor/Editor/Playground/index.tsx
Outdated
Show resolved
Hide resolved
34f1c7e
to
48fc82c
Compare
default: | ||
return 'default' | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Classic hash cc @ferranete
Modal to import logs while testing the evaluation in the editor
48fc82c
to
1db6b6d
Compare
Implements the import logs modal