Skip to content

Commit a81a0a6

Browse files
authored
enhance: openapi: better confirmation prompts (#196)
Signed-off-by: Grant Linville <[email protected]>
1 parent 2682446 commit a81a0a6

File tree

3 files changed

+48
-2
lines changed

3 files changed

+48
-2
lines changed

components/script/messages.tsx

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,10 @@ const Message = ({
3939
noAvatar?: boolean;
4040
restart?: () => void;
4141
}) => {
42+
if (message === undefined) {
43+
return null;
44+
}
45+
4246
switch (message.type) {
4347
case MessageType.User:
4448
return (

components/script/messages/confirmForm.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ const ConfirmForm = ({
4646
{message}
4747
</Markdown>
4848
{command && (
49-
<Code className="ml-4">
49+
<Code className="ml-4 whitespace-pre-wrap">
5050
{command.startsWith('Running')
5151
? command.replace('Running', '').replace(/`/g, '')
5252
: command.replace(/`/g, '')}

components/script/useChatSocket.tsx

Lines changed: 43 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,8 @@ const useChatSocket = (isEmpty?: boolean) => {
3333
const latestAgentMessageIndex = useRef<number>(-1);
3434
const trustedRef = useRef<Record<string, boolean>>({});
3535
const trustedRepoPrefixesRef = useRef<string[]>([...initiallyTrustedRepos]);
36+
// trustedOpenAPIRef contains a mapping of OpenAPI run tools to OpenAPI operation names that have been trusted.
37+
const trustedOpenAPIRef = useRef<Record<string, Record<string, boolean>>>({});
3638

3739
// update the refs as the state changes
3840
useEffect(() => {
@@ -201,7 +203,9 @@ const useChatSocket = (isEmpty?: boolean) => {
201203
}
202204

203205
let confirmMessage = `Proceed with calling the ${frame.tool.name} tool?`;
204-
if (frame.displayText) {
206+
if (frame.tool.instructions?.startsWith('#!sys.openapi')) {
207+
confirmMessage = `Proceed with running the following API operation (or allow all runs of this operation)?`;
208+
} else if (frame.displayText) {
205209
const tool = frame.tool?.name?.replace('sys.', '');
206210
confirmMessage = frame.tool?.source?.repo
207211
? `Proceed with running the following (or allow all calls from the **${trimRepo(frame.tool?.source.repo!.Root)}** repo)?`
@@ -278,6 +282,28 @@ const useChatSocket = (isEmpty?: boolean) => {
278282
const alreadyAllowed = (frame: CallFrame): boolean => {
279283
if (!frame.tool) return false;
280284

285+
if (frame.tool.instructions?.startsWith('#!sys.openapi')) {
286+
// If the tool is an OpenAPI tool to list operations or get the schema for an operation, allow it.
287+
const instructions = frame.tool.instructions.split(' ');
288+
if (
289+
instructions.length > 2 &&
290+
(instructions[1] == 'list' || instructions[1] == 'get-schema')
291+
) {
292+
return true;
293+
}
294+
295+
// If the tool is an OpenAPI tool to run an operation, check if it has been trusted.
296+
if (!frame.tool.name) {
297+
return false;
298+
}
299+
300+
const operation = JSON.parse(frame.input as string)['operation'];
301+
return (
302+
trustedOpenAPIRef.current[frame.tool.name] &&
303+
trustedOpenAPIRef.current[frame.tool.name][operation]
304+
);
305+
}
306+
281307
// Check if the tool has already been allowed
282308
if (frame.tool.name && trustedRef.current[frame.tool.name]) return true;
283309

@@ -304,6 +330,22 @@ const useChatSocket = (isEmpty?: boolean) => {
304330
const addTrustedFor = (frame: CallFrame) => {
305331
if (!frame.tool) return () => {};
306332

333+
if (
334+
frame.tool.instructions &&
335+
frame.tool.name &&
336+
frame.tool.instructions.startsWith('#!sys.openapi')
337+
) {
338+
return () => {
339+
const toolName = frame.tool?.name ?? ''; // Not possible for this to be null, but I have to satisfy the type checker.
340+
const operation = JSON.parse(frame.input as string)['operation'];
341+
342+
if (!trustedOpenAPIRef.current[toolName]) {
343+
trustedOpenAPIRef.current[toolName] = {};
344+
}
345+
trustedOpenAPIRef.current[toolName][operation] = true;
346+
};
347+
}
348+
307349
return frame.tool.source?.repo
308350
? () => {
309351
const repo = frame.tool!.source?.repo!.Root;

0 commit comments

Comments
 (0)