Last active
July 30, 2023 10:37
-
-
Save tarasglek/cff4ebfb184c54f505cd46310918f541 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* 1. Name of your function (must be unique) */ | |
export const name = "shell_cmd"; | |
/* 2. Description of function, used to describe what it does to an LLM */ | |
export const description = "This executes shell commands. It's not able to execute interactive commands like vim, prefer to use tee, etc instead"; | |
/** | |
* 3. A JSON Schema defining the function's parameters. See: | |
* | |
* - https://platform.openai.com/docs/guides/gpt/function-calling | |
* - https://json-schema.org/learn/getting-started-step-by-step | |
*/ | |
export const parameters = { | |
type: "object", | |
properties: { | |
cmd: { | |
type: "string", | |
description: "Valid bash command", | |
}, | |
websocket_url: { | |
type: "string", | |
description: "Websocket url, only needed on first run", | |
} | |
}, | |
required: ["cmd"], | |
}; | |
export default async function (value) { | |
const cmd = value.cmd; | |
const websocket_url = value.websocket_url; | |
async function connectWebSocket(url) { | |
return new Promise((resolve, reject) => { | |
const socket = new WebSocket(url); | |
socket.binaryType = "arraybuffer"; | |
socket.addEventListener("open", () => resolve(socket)); | |
socket.addEventListener("error", (error) => reject(error)); | |
}); | |
} | |
function format_error(error) { | |
console.log(error); | |
return("**WebSocket connection error**:\n```\n" + error + "\n```"); | |
} | |
if (!window.socket || window.socket.readyState !== WebSocket.OPEN) { | |
if (!websocket_url) { | |
return ("**Not Connected!**\nPlease run the following command and tell chatcraft to connect that websocket url when invoking this function:\n```bash\n" + | |
`TERM=vt100 PROMPT_COMMAND='echo -n "[$(pwd)]"' websocat --exit-on-eof ws-l:0.0.0.0:8810 sh-c:'bash --rcfile emptyrc -i 2>&1' --binary` + | |
"\n#Run the following command in another shell to expose via public internet(dangerous)\n" + | |
"ssh -R 80:localhost:8810 serveo.net" + | |
"\n#^ will give you a url like http://foo.serveo.net, which you can pass as websocket url to chatcraft" + | |
"\n```"); | |
} | |
try { | |
window.socket = await connectWebSocket( | |
websocket_url | |
); | |
} catch (error) { | |
return format_error(error); | |
} | |
} | |
const sendMessage = (socket, message) => { | |
const buffer = new TextEncoder().encode(message + "\n"); | |
socket.send(buffer); | |
}; | |
const receiveMessages = (socket, timeout) => { | |
return new Promise((resolve) => { | |
let buffer = ""; | |
const handleMessage = (event) => { | |
const message = new TextDecoder().decode(new Uint8Array(event.data)); | |
buffer += message; | |
console.log(JSON.stringify(buffer)); | |
}; | |
socket.addEventListener("message", handleMessage); | |
setTimeout(() => { | |
socket.removeEventListener("message", handleMessage); | |
resolve(buffer); | |
}, timeout); | |
}); | |
}; | |
try { | |
sendMessage(window.socket, cmd); | |
const response = await receiveMessages(window.socket, 2000); | |
console.log(response); | |
return "\n```bash\n"+response+"\n```"; | |
} catch (error) { | |
return format_error(error); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment