Skip to content

Commit

Permalink
Adds chatGPT bundle and create prompt mask
Browse files Browse the repository at this point in the history
  • Loading branch information
ap0k4 committed Apr 28, 2024
1 parent e277bdd commit 4227738
Show file tree
Hide file tree
Showing 5 changed files with 190 additions and 1 deletion.
2 changes: 2 additions & 0 deletions packages/app/bundles/apiContext.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import os from 'protolib/bundles/os/context'
import os2 from 'protolib/bundles/os/context2'
import utils from 'protolib/bundles/utils/context'
import keys from 'protolib/bundles/keys/context'
import chatGPT from 'protolib/bundles/chatgpt/context'
export default {
onEvent,
emitEvent,
Expand All @@ -25,6 +26,7 @@ export default {
sendMailWithResend,
executeAutomation,
keys,
chatGPT,
flow,
flow2,
object,
Expand Down
4 changes: 3 additions & 1 deletion packages/app/bundles/masks.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import osMasks from 'protolib/bundles/os/masks'
import osMasks2 from 'protolib/bundles/os/masks2'
import utilsMasks from 'protolib/bundles/utils/masks'
import keyMasks from 'protolib/bundles/keys/masks'
import chatGPTMasks from 'protolib/bundles/chatgpt/masks'

const paths = {
devices: [
Expand Down Expand Up @@ -64,7 +65,8 @@ export const getFlowsCustomComponents = (path: string, queryParams: {}) => {
...osMasks,
...osMasks2,
...keyMasks,
...utilsMasks
...utilsMasks,
...chatGPTMasks
]
return []
}
Expand Down
105 changes: 105 additions & 0 deletions packages/protolib/bundles/chatgpt/context/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@

const chatGPTSession = async ({
apiKey = process.env.OPENAI_API_KEY,
done = (message) => { },
error = (error) => { },
...props
}: ChatGPTRequest) => {
const body: GPT4VCompletionRequest = {
model: "gpt-4-1106-preview",
max_tokens: 4096,
...props
}

if (!apiKey) {
error("No api Key provided")
return
}

try {
const response = await fetch("https://api.openai.com/v1/chat/completions", {
method: "POST",
headers: {
"Content-Type": "application/json",
Authorization: "Bearer " + apiKey,
},
body: JSON.stringify(body),
});
const json = await response.json();
if (done) done(json)
return json
} catch (e) {
if (error) error(e)
return
}
}

const chatGPTPrompt = async ({
message,
...props

}: ChatGPTRequest & { message: string }) => {
let response = await chatGPTSession({
messages: [
{
role: "user",
content: message
}
],
...props,
done: (response) => {
let message = ""
if(response.choices && response.choices.length){
message = response.choices[0].message.content
}
if(props.done) props.done(message)
}
})

if(!response.choices || !response.choices.length){ return "" }

return response.choices[0].message.content
}

type ChatGPTRequest = {
apiKey?: string;
done?: (message: any) => any;
error?: (error: any) => any;
} & GPT4VCompletionRequest

type GPT4VCompletionRequest = {
model: "gpt-4-vision-preview" | "gpt-4-1106-preview" | "gpt-4" | "gpt-4-32k" | "gpt-4-0613" | "gpt-4-32k-0613" | "gpt-4-0314" | "gpt-4-32k-0314"; // https://platform.openai.com/docs/models/overview
messages: Message[];
functions?: any[] | undefined;
function_call?: any | undefined;
stream?: boolean | undefined;
temperature?: number | undefined;
top_p?: number | undefined;
max_tokens?: number | undefined;
n?: number | undefined;
best_of?: number | undefined;
frequency_penalty?: number | undefined;
presence_penalty?: number | undefined;
logit_bias?:
| {
[x: string]: number;
}
| undefined;
stop?: (string[] | string) | undefined;
};

type Message = {
role: "system" | "user" | "assistant" | "function";
content: MessageContent;
name?: string | undefined;
}

type MessageContent =
| string // String prompt
| (string | { type: "image_url"; image_url: string })[]; // Image asset


export default {
chatGPTSession,
chatGPTPrompt
}
75 changes: 75 additions & 0 deletions packages/protolib/bundles/chatgpt/masks/ChatGPTPrompt.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
import { Node, NodeOutput, FallbackPort, NodeParams, filterConnection, getId, connectNodes, filterObject, restoreObject } from 'protoflow';
import { useColorFromPalette } from 'protoflow/src/diagram/Theme'
import { MessageCircle } from 'lucide-react'

const ChatGPTPrompt = ({ node = {}, nodeData = {}, children }: any) => {
const color = useColorFromPalette(11)
return (
<Node icon={MessageCircle} node={node} isPreview={!node.id} title='Chat GPT Prompt' color={color} id={node.id} skipCustom={true}>
<NodeParams id={node.id} params={[{ label: 'message', field: 'mask-message', type: 'input' }]} />
<NodeParams id={node.id} params={[{ label: 'model', field: 'mask-model', type: 'select', data: ["gpt-4-1106-preview", "gpt-4-vision-preview", "gpt-4", "gpt-4-32k", "gpt-4-0613", "gpt-4-32k-0613", "gpt-4-0314", "gpt-4-32k-0314"] }]} />
<NodeParams id={node.id} params={[{ label: 'max tokens', field: 'mask-max_tokens', type: 'input' }]} />
<NodeParams id={node.id} params={[{ label: 'api key', field: 'mask-apikey', type: 'input' }]} />
<div style={{ height: '30px' }} />
<NodeOutput id={node.id} type={'input'} label={'On Read'} vars={['message']} handleId={'mask-done'} />
<NodeOutput id={node.id} type={'input'} label={'Error'} vars={['err']} handleId={'mask-error'} />
</Node>
)
}

export default {
id: 'chatGPT.chatGPTPrompt',
type: 'CallExpression',
category: "System",
keywords: ["prompt", "chat", "gpt", "chatgpt", "openai", "ai", "bot"],
check: (node, nodeData) => {
return node.type == "CallExpression" && nodeData.to?.startsWith('context.chatGPT.chatGPTPrompt')
},
getComponent: (node, nodeData, children) => <ChatGPTPrompt node={node} nodeData={nodeData} children={children} />,
filterChildren: filterObject({
keys: {
message: 'input',
apiKey: 'input',
model: 'input',
max_tokens: 'input',
done: 'output',
error: 'output'
}
}),
restoreChildren: restoreObject({
keys: {
message: 'input',
apiKey: 'input',
model: 'input',
max_tokens: 'input',
done: { params: { 'param-done': { key: "message" } } },
error: { params: { 'param-error': { key: "err" } } }
}
}),
getInitialData: () => {
return {
await: true,
to: 'context.chatGPT.chatGPTPrompt',
"param-1": {
value: "{}",
kind: "Identifier"
},
"mask-apikey": {
value: "",
kind: "StringLiteral"
},
"mask-model": {
value: "gpt-4-1106-preview",
kind: "StringLiteral"
},
"mask-message": {
value: "",
kind: "StringLiteral"
},
"mask-max_tokens": {
value: "4096",
kind: "NumericLiteral"
}
}
}
}
5 changes: 5 additions & 0 deletions packages/protolib/bundles/chatgpt/masks/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
import ChatGPTPrompt from './ChatGPTPrompt'

export default [
ChatGPTPrompt
]

0 comments on commit 4227738

Please sign in to comment.