mirror of
https://github.com/supabase/supabase.git
synced 2026-10-05 09:25:06 +03:00
Migrate all apps and packages to use OpenAI v4 lib (#19270)
* Migrate all apps and packages to use OpenAI v4 lib. * Minor fix. * refactor: improve types for completion chunks --------- Co-authored-by: Greg Richardson <greg.nmr@gmail.com>
This commit is contained in:
1 parent
38dfd14c31
commit
33f617a6cc
8 files changed
+90
-237
No files matched your search
@@ -63,8 +63,7 @@
|
||||
"monaco-editor": "0.33.0",
|
||||
"next": "^13.5.6",
|
||||
"next-themes": "^0.2.1",
|
||||
"openai-old": "npm:openai@^3.3.0",
|
||||
"openai": "^4.0.0",
|
||||
"openai": "^4.20.1",
|
||||
"openapi-fetch": "^0.6.1",
|
||||
"p-queue": "^6.6.2",
|
||||
"papaparse": "^5.3.1",
|
||||
|
||||
@@ -4,12 +4,7 @@ import { isError } from 'data/utils/error-check'
|
||||
import { jsonrepair } from 'jsonrepair'
|
||||
import apiWrapper from 'lib/api/apiWrapper'
|
||||
import { NextApiRequest, NextApiResponse } from 'next'
|
||||
import type {
|
||||
ChatCompletionRequestMessage,
|
||||
CreateChatCompletionRequest,
|
||||
CreateChatCompletionResponse,
|
||||
ErrorResponse,
|
||||
} from 'openai-old'
|
||||
import { OpenAI } from 'openai'
|
||||
|
||||
const openAiKey = process.env.OPENAI_KEY
|
||||
|
||||
@@ -23,7 +18,10 @@ const debugSqlSchema = SchemaBuilder.emptySchema()
|
||||
|
||||
type DebugSqlResult = typeof debugSqlSchema.T
|
||||
|
||||
const completionFunctions = {
|
||||
const completionFunctions: Record<
|
||||
string,
|
||||
OpenAI.Chat.Completions.ChatCompletionCreateParams.Function
|
||||
> = {
|
||||
debugSql: {
|
||||
name: 'debugSql',
|
||||
description: stripIndent`
|
||||
@@ -38,7 +36,7 @@ const completionFunctions = {
|
||||
- Use vector(384) data type for any embedding/vector related query
|
||||
- Always use double apostrophe in SQL strings (eg. 'Night''s watch')
|
||||
`,
|
||||
parameters: debugSqlSchema.schema,
|
||||
parameters: debugSqlSchema.schema as Record<string, unknown>,
|
||||
},
|
||||
}
|
||||
|
||||
@@ -61,6 +59,7 @@ async function handler(req: NextApiRequest, res: NextApiResponse) {
|
||||
}
|
||||
|
||||
export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
const openAI = new OpenAI({ apiKey: openAiKey })
|
||||
const {
|
||||
body: { errorMessage, sql, entityDefinitions },
|
||||
} = req
|
||||
@@ -69,7 +68,7 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
const maxCompletionTokenCount = 2048
|
||||
const hasEntityDefinitions = entityDefinitions !== undefined && entityDefinitions.length > 0
|
||||
|
||||
const completionMessages: ChatCompletionRequestMessage[] = []
|
||||
const completionMessages: OpenAI.Chat.Completions.ChatCompletionMessageParam[] = []
|
||||
|
||||
if (hasEntityDefinitions) {
|
||||
completionMessages.push({
|
||||
@@ -98,7 +97,7 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
}
|
||||
)
|
||||
|
||||
const completionOptions: CreateChatCompletionRequest = {
|
||||
const completionOptions: OpenAI.Chat.Completions.ChatCompletionCreateParamsNonStreaming = {
|
||||
model,
|
||||
messages: completionMessages,
|
||||
max_tokens: maxCompletionTokenCount,
|
||||
@@ -110,20 +109,13 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
stream: false,
|
||||
}
|
||||
|
||||
const response = await fetch('https://api.openai.com/v1/chat/completions', {
|
||||
headers: {
|
||||
Authorization: `Bearer ${openAiKey}`,
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
method: 'POST',
|
||||
body: JSON.stringify(completionOptions),
|
||||
})
|
||||
let completionResponse: OpenAI.Chat.Completions.ChatCompletion
|
||||
try {
|
||||
completionResponse = await openAI.chat.completions.create(completionOptions)
|
||||
} catch (error: any) {
|
||||
console.error(`AI SQL debugging failed: ${error.message}`)
|
||||
|
||||
if (!response.ok) {
|
||||
const errorResponse: ErrorResponse = await response.json()
|
||||
console.error(`AI SQL debugging failed: ${errorResponse.error.message}`)
|
||||
|
||||
if ('code' in errorResponse.error && errorResponse.error.code === 'context_length_exceeded') {
|
||||
if ('code' in error && error.code === 'context_length_exceeded') {
|
||||
if (hasEntityDefinitions) {
|
||||
const definitionsLength = entityDefinitions.reduce(
|
||||
(sum: number, def: string) => sum + def.length,
|
||||
@@ -149,8 +141,6 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
})
|
||||
}
|
||||
|
||||
const completionResponse: CreateChatCompletionResponse = await response.json()
|
||||
|
||||
const [firstChoice] = completionResponse.choices
|
||||
|
||||
const sqlResponseString = firstChoice.message?.function_call?.arguments
|
||||
|
||||
@@ -4,12 +4,7 @@ import { isError } from 'data/utils/error-check'
|
||||
import { jsonrepair } from 'jsonrepair'
|
||||
import apiWrapper from 'lib/api/apiWrapper'
|
||||
import { NextApiRequest, NextApiResponse } from 'next'
|
||||
import type {
|
||||
ChatCompletionRequestMessage,
|
||||
CreateChatCompletionRequest,
|
||||
CreateChatCompletionResponse,
|
||||
ErrorResponse,
|
||||
} from 'openai-old'
|
||||
import { OpenAI } from 'openai'
|
||||
|
||||
const openAiKey = process.env.OPENAI_KEY
|
||||
|
||||
@@ -29,11 +24,14 @@ const editSqlSchema = SchemaBuilder.emptySchema().addString('sql', {
|
||||
|
||||
type EditSqlResult = typeof editSqlSchema.T
|
||||
|
||||
const completionFunctions = {
|
||||
const completionFunctions: Record<
|
||||
string,
|
||||
OpenAI.Chat.Completions.ChatCompletionCreateParams.Function
|
||||
> = {
|
||||
editSql: {
|
||||
name: 'editSql',
|
||||
description: "Edits a Postgres SQL query based on the user's instructions",
|
||||
parameters: editSqlSchema.schema,
|
||||
parameters: editSqlSchema.schema as Record<string, unknown>,
|
||||
},
|
||||
}
|
||||
|
||||
@@ -60,11 +58,12 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
body: { prompt, sql, entityDefinitions },
|
||||
} = req
|
||||
|
||||
const openAI = new OpenAI({ apiKey: openAiKey })
|
||||
const model = 'gpt-3.5-turbo-0613'
|
||||
const maxCompletionTokenCount = 2048
|
||||
const hasEntityDefinitions = entityDefinitions !== undefined && entityDefinitions.length > 0
|
||||
|
||||
const completionMessages: ChatCompletionRequestMessage[] = []
|
||||
const completionMessages: OpenAI.Chat.Completions.ChatCompletionMessageParam[] = []
|
||||
|
||||
if (hasEntityDefinitions) {
|
||||
completionMessages.push({
|
||||
@@ -90,7 +89,7 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
}
|
||||
)
|
||||
|
||||
const completionOptions: CreateChatCompletionRequest = {
|
||||
const completionOptions: OpenAI.Chat.Completions.ChatCompletionCreateParamsNonStreaming = {
|
||||
model,
|
||||
messages: completionMessages,
|
||||
max_tokens: maxCompletionTokenCount,
|
||||
@@ -102,26 +101,17 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
stream: false,
|
||||
}
|
||||
|
||||
const response = await fetch('https://api.openai.com/v1/chat/completions', {
|
||||
headers: {
|
||||
Authorization: `Bearer ${openAiKey}`,
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
method: 'POST',
|
||||
body: JSON.stringify(completionOptions),
|
||||
})
|
||||
|
||||
if (!response.ok) {
|
||||
const errorResponse: ErrorResponse = await response.json()
|
||||
console.error(`AI SQL editing failed: ${errorResponse.error.message}`)
|
||||
|
||||
if ('code' in errorResponse.error && errorResponse.error.code === 'context_length_exceeded') {
|
||||
let completionResponse: OpenAI.Chat.Completions.ChatCompletion
|
||||
try {
|
||||
completionResponse = await openAI.chat.completions.create(completionOptions)
|
||||
} catch (error: any) {
|
||||
console.error(`AI SQL editing failed: ${error.message}`)
|
||||
if ('code' in error && error.code === 'context_length_exceeded') {
|
||||
if (hasEntityDefinitions) {
|
||||
const definitionsLength = entityDefinitions.reduce(
|
||||
(sum: number, def: string) => sum + def.length,
|
||||
0
|
||||
)
|
||||
|
||||
if (definitionsLength > sql.length) {
|
||||
return res.status(400).json({
|
||||
error:
|
||||
@@ -129,20 +119,16 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
return res.status(400).json({
|
||||
error:
|
||||
'Your SQL query is too large for Supabase AI to ingest. Try splitting it into smaller queries.',
|
||||
})
|
||||
}
|
||||
|
||||
return res.status(500).json({
|
||||
error: 'There was an unknown error editing the SQL snippet. Please try again.',
|
||||
})
|
||||
}
|
||||
|
||||
const completionResponse: CreateChatCompletionResponse = await response.json()
|
||||
|
||||
const [firstChoice] = completionResponse.choices
|
||||
|
||||
const sqlResponseString = firstChoice.message?.function_call?.arguments
|
||||
|
||||
@@ -4,12 +4,7 @@ import { isError } from 'data/utils/error-check'
|
||||
import { jsonrepair } from 'jsonrepair'
|
||||
import apiWrapper from 'lib/api/apiWrapper'
|
||||
import { NextApiRequest, NextApiResponse } from 'next'
|
||||
import type {
|
||||
ChatCompletionRequestMessage,
|
||||
CreateChatCompletionRequest,
|
||||
CreateChatCompletionResponse,
|
||||
ErrorResponse,
|
||||
} from 'openai-old'
|
||||
import { OpenAI } from 'openai'
|
||||
|
||||
const openAiKey = process.env.OPENAI_KEY
|
||||
|
||||
@@ -34,11 +29,14 @@ const generateSqlSchema = SchemaBuilder.emptySchema()
|
||||
|
||||
type GenerateSqlResult = typeof generateSqlSchema.T
|
||||
|
||||
const completionFunctions = {
|
||||
const completionFunctions: Record<
|
||||
string,
|
||||
OpenAI.Chat.Completions.ChatCompletionCreateParams.Function
|
||||
> = {
|
||||
generateSql: {
|
||||
name: 'generateSql',
|
||||
description: 'Generates Postgres SQL based on a natural language prompt',
|
||||
parameters: generateSqlSchema.schema,
|
||||
parameters: generateSqlSchema.schema as Record<string, unknown>,
|
||||
},
|
||||
}
|
||||
|
||||
@@ -61,6 +59,7 @@ async function handler(req: NextApiRequest, res: NextApiResponse) {
|
||||
}
|
||||
|
||||
export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
const openAI = new OpenAI({ apiKey: openAiKey })
|
||||
const {
|
||||
body: { prompt, entityDefinitions },
|
||||
} = req
|
||||
@@ -69,7 +68,7 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
const maxCompletionTokenCount = 1024
|
||||
const hasEntityDefinitions = entityDefinitions !== undefined && entityDefinitions.length > 0
|
||||
|
||||
const completionMessages: ChatCompletionRequestMessage[] = []
|
||||
const completionMessages: OpenAI.Chat.Completions.ChatCompletionMessageParam[] = []
|
||||
|
||||
if (hasEntityDefinitions) {
|
||||
completionMessages.push({
|
||||
@@ -86,7 +85,7 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
content: prompt,
|
||||
})
|
||||
|
||||
const completionOptions: CreateChatCompletionRequest = {
|
||||
const completionOptions: OpenAI.Chat.Completions.ChatCompletionCreateParamsNonStreaming = {
|
||||
model,
|
||||
messages: completionMessages,
|
||||
max_tokens: maxCompletionTokenCount,
|
||||
@@ -98,24 +97,13 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
stream: false,
|
||||
}
|
||||
|
||||
const response = await fetch('https://api.openai.com/v1/chat/completions', {
|
||||
headers: {
|
||||
Authorization: `Bearer ${openAiKey}`,
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
method: 'POST',
|
||||
body: JSON.stringify(completionOptions),
|
||||
})
|
||||
let completionResponse: OpenAI.Chat.Completions.ChatCompletion
|
||||
try {
|
||||
completionResponse = await openAI.chat.completions.create(completionOptions)
|
||||
} catch (error: any) {
|
||||
console.error(`AI SQL generation failed: ${error.message}`)
|
||||
|
||||
if (!response.ok) {
|
||||
const errorResponse: ErrorResponse = await response.json()
|
||||
console.error(`AI SQL generation failed: ${errorResponse.error.message}`)
|
||||
|
||||
if (
|
||||
'code' in errorResponse.error &&
|
||||
errorResponse.error.code === 'context_length_exceeded' &&
|
||||
hasEntityDefinitions
|
||||
) {
|
||||
if ('code' in error && error.code === 'context_length_exceeded' && hasEntityDefinitions) {
|
||||
return res.status(400).json({
|
||||
error:
|
||||
'Your database metadata is too large for Supabase AI to ingest. Try disabling database metadata in AI settings.',
|
||||
@@ -127,8 +115,6 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
})
|
||||
}
|
||||
|
||||
const completionResponse: CreateChatCompletionResponse = await response.json()
|
||||
|
||||
const [firstChoice] = completionResponse.choices
|
||||
|
||||
const sqlResponseString = firstChoice.message?.function_call?.arguments
|
||||
|
||||
@@ -4,12 +4,7 @@ import { isError } from 'data/utils/error-check'
|
||||
import { jsonrepair } from 'jsonrepair'
|
||||
import apiWrapper from 'lib/api/apiWrapper'
|
||||
import { NextApiRequest, NextApiResponse } from 'next'
|
||||
import type {
|
||||
ChatCompletionRequestMessage,
|
||||
CreateChatCompletionRequest,
|
||||
CreateChatCompletionResponse,
|
||||
ErrorResponse,
|
||||
} from 'openai-old'
|
||||
import { OpenAI } from 'openai'
|
||||
|
||||
const openAiKey = process.env.OPENAI_KEY
|
||||
|
||||
@@ -29,11 +24,11 @@ const generateTitleSchema = SchemaBuilder.emptySchema()
|
||||
|
||||
type GenerateTitleResult = typeof generateTitleSchema.T
|
||||
|
||||
const completionFunctions = {
|
||||
const completionFunctions: Record<string, OpenAI.ChatCompletionCreateParams.Function> = {
|
||||
generateTitle: {
|
||||
name: 'generateTitle',
|
||||
description: 'Generates a short title and detailed description for a Postgres SQL snippet',
|
||||
parameters: generateTitleSchema.schema,
|
||||
parameters: generateTitleSchema.schema as Record<string, unknown>,
|
||||
},
|
||||
}
|
||||
|
||||
@@ -56,6 +51,7 @@ async function handler(req: NextApiRequest, res: NextApiResponse) {
|
||||
}
|
||||
|
||||
export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
const openAI = new OpenAI({ apiKey: openAiKey })
|
||||
const {
|
||||
body: { sql },
|
||||
} = req
|
||||
@@ -63,14 +59,14 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
const model = 'gpt-3.5-turbo-0613'
|
||||
const maxCompletionTokenCount = 1024
|
||||
|
||||
const completionMessages: ChatCompletionRequestMessage[] = [
|
||||
const completionMessages: OpenAI.Chat.Completions.ChatCompletionMessageParam[] = [
|
||||
{
|
||||
role: 'user',
|
||||
content: sql,
|
||||
},
|
||||
]
|
||||
|
||||
const completionOptions: CreateChatCompletionRequest = {
|
||||
const completionOptions: OpenAI.Chat.Completions.ChatCompletionCreateParamsNonStreaming = {
|
||||
model,
|
||||
messages: completionMessages,
|
||||
max_tokens: maxCompletionTokenCount,
|
||||
@@ -82,20 +78,13 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
stream: false,
|
||||
}
|
||||
|
||||
const response = await fetch('https://api.openai.com/v1/chat/completions', {
|
||||
headers: {
|
||||
Authorization: `Bearer ${openAiKey}`,
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
method: 'POST',
|
||||
body: JSON.stringify(completionOptions),
|
||||
})
|
||||
let completionResponse: OpenAI.Chat.Completions.ChatCompletion
|
||||
try {
|
||||
completionResponse = await openAI.chat.completions.create(completionOptions)
|
||||
} catch (error: any) {
|
||||
console.error(`AI title generation failed: ${error.message}`)
|
||||
|
||||
if (!response.ok) {
|
||||
const errorResponse: ErrorResponse = await response.json()
|
||||
console.error(`AI title generation failed: ${errorResponse.error.message}`)
|
||||
|
||||
if ('code' in errorResponse.error && errorResponse.error.code === 'context_length_exceeded') {
|
||||
if ('code' in error && error.code === 'context_length_exceeded') {
|
||||
return res.status(400).json({
|
||||
error:
|
||||
'Your SQL query is too large for Supabase AI to ingest. Try splitting it into smaller queries.',
|
||||
@@ -107,8 +96,6 @@ export async function handlePost(req: NextApiRequest, res: NextApiResponse) {
|
||||
})
|
||||
}
|
||||
|
||||
const completionResponse: CreateChatCompletionResponse = await response.json()
|
||||
|
||||
const [firstChoice] = completionResponse.choices
|
||||
|
||||
const titleResponseString = firstChoice.message?.function_call?.arguments
|
||||
|
||||
Generated
+24
-108
@@ -248,6 +248,7 @@
|
||||
"version": "18.18.13",
|
||||
"resolved": "https://registry.npmjs.org/@types/node/-/node-18.18.13.tgz",
|
||||
"integrity": "sha512-vXYZGRrSCreZmq1rEjMRLXJhiy8MrIeVasx+PCVlP414N7CJLHnMf+juVvjdprHyH+XRy3zKZLHeNueOpJCn0g==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"undici-types": "~5.26.4"
|
||||
}
|
||||
@@ -451,25 +452,6 @@
|
||||
}
|
||||
}
|
||||
},
|
||||
"apps/database-new/node_modules/openai": {
|
||||
"version": "4.20.0",
|
||||
"resolved": "https://registry.npmjs.org/openai/-/openai-4.20.0.tgz",
|
||||
"integrity": "sha512-VbAYerNZFfIIeESS+OL9vgDkK8Mnri55n+jN0UN/HZeuM0ghGh6nDN6UGRZxslNgyJ7XmY/Ca9DO4YYyvrszGA==",
|
||||
"dependencies": {
|
||||
"@types/node": "^18.11.18",
|
||||
"@types/node-fetch": "^2.6.4",
|
||||
"abort-controller": "^3.0.0",
|
||||
"agentkeepalive": "^4.2.1",
|
||||
"digest-fetch": "^1.3.0",
|
||||
"form-data-encoder": "1.7.2",
|
||||
"formdata-node": "^4.3.2",
|
||||
"node-fetch": "^2.6.7",
|
||||
"web-streams-polyfill": "^3.2.1"
|
||||
},
|
||||
"bin": {
|
||||
"openai": "bin/cli"
|
||||
}
|
||||
},
|
||||
"apps/database-new/node_modules/resolve": {
|
||||
"version": "2.0.0-next.5",
|
||||
"resolved": "https://registry.npmjs.org/resolve/-/resolve-2.0.0-next.5.tgz",
|
||||
@@ -580,6 +562,7 @@
|
||||
},
|
||||
"apps/docs/node_modules/@types/node": {
|
||||
"version": "18.18.8",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"undici-types": "~5.26.4"
|
||||
@@ -662,25 +645,6 @@
|
||||
],
|
||||
"license": "MIT"
|
||||
},
|
||||
"apps/docs/node_modules/openai": {
|
||||
"version": "4.20.0",
|
||||
"resolved": "https://registry.npmjs.org/openai/-/openai-4.20.0.tgz",
|
||||
"integrity": "sha512-VbAYerNZFfIIeESS+OL9vgDkK8Mnri55n+jN0UN/HZeuM0ghGh6nDN6UGRZxslNgyJ7XmY/Ca9DO4YYyvrszGA==",
|
||||
"dependencies": {
|
||||
"@types/node": "^18.11.18",
|
||||
"@types/node-fetch": "^2.6.4",
|
||||
"abort-controller": "^3.0.0",
|
||||
"agentkeepalive": "^4.2.1",
|
||||
"digest-fetch": "^1.3.0",
|
||||
"form-data-encoder": "1.7.2",
|
||||
"formdata-node": "^4.3.2",
|
||||
"node-fetch": "^2.6.7",
|
||||
"web-streams-polyfill": "^3.2.1"
|
||||
},
|
||||
"bin": {
|
||||
"openai": "bin/cli"
|
||||
}
|
||||
},
|
||||
"apps/docs/node_modules/puppeteer": {
|
||||
"version": "16.2.0",
|
||||
"resolved": "https://registry.npmjs.org/puppeteer/-/puppeteer-16.2.0.tgz",
|
||||
@@ -786,8 +750,7 @@
|
||||
"monaco-editor": "0.33.0",
|
||||
"next": "^13.5.6",
|
||||
"next-themes": "^0.2.1",
|
||||
"openai": "^4.0.0",
|
||||
"openai-old": "npm:openai@^3.3.0",
|
||||
"openai": "^4.20.1",
|
||||
"openapi-fetch": "^0.6.1",
|
||||
"p-queue": "^6.6.2",
|
||||
"papaparse": "^5.3.1",
|
||||
@@ -886,13 +849,6 @@
|
||||
"glob": "7.1.7"
|
||||
}
|
||||
},
|
||||
"apps/studio/node_modules/@types/node": {
|
||||
"version": "18.18.10",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"undici-types": "~5.26.4"
|
||||
}
|
||||
},
|
||||
"apps/studio/node_modules/ajv": {
|
||||
"version": "8.12.0",
|
||||
"license": "MIT",
|
||||
@@ -1023,24 +979,6 @@
|
||||
"version": "1.0.0",
|
||||
"license": "MIT"
|
||||
},
|
||||
"apps/studio/node_modules/openai": {
|
||||
"version": "4.19.0",
|
||||
"license": "Apache-2.0",
|
||||
"dependencies": {
|
||||
"@types/node": "^18.11.18",
|
||||
"@types/node-fetch": "^2.6.4",
|
||||
"abort-controller": "^3.0.0",
|
||||
"agentkeepalive": "^4.2.1",
|
||||
"digest-fetch": "^1.3.0",
|
||||
"form-data-encoder": "1.7.2",
|
||||
"formdata-node": "^4.3.2",
|
||||
"node-fetch": "^2.6.7",
|
||||
"web-streams-polyfill": "^3.2.1"
|
||||
},
|
||||
"bin": {
|
||||
"openai": "bin/cli"
|
||||
}
|
||||
},
|
||||
"apps/studio/node_modules/resolve": {
|
||||
"version": "2.0.0-next.5",
|
||||
"dev": true,
|
||||
@@ -17664,24 +17602,6 @@
|
||||
"node": ">=0.4.0"
|
||||
}
|
||||
},
|
||||
"node_modules/follow-redirects": {
|
||||
"version": "1.15.3",
|
||||
"funding": [
|
||||
{
|
||||
"type": "individual",
|
||||
"url": "https://github.com/sponsors/RubenVerborgh"
|
||||
}
|
||||
],
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=4.0"
|
||||
},
|
||||
"peerDependenciesMeta": {
|
||||
"debug": {
|
||||
"optional": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"node_modules/for-each": {
|
||||
"version": "0.3.3",
|
||||
"license": "MIT",
|
||||
@@ -26415,34 +26335,30 @@
|
||||
}
|
||||
},
|
||||
"node_modules/openai": {
|
||||
"version": "3.3.0",
|
||||
"license": "MIT",
|
||||
"version": "4.20.1",
|
||||
"resolved": "https://registry.npmjs.org/openai/-/openai-4.20.1.tgz",
|
||||
"integrity": "sha512-Dd3q8EvINfganZFtg6V36HjrMaihqRgIcKiHua4Nq9aw/PxOP48dhbsk8x5klrxajt5Lpnc1KTOG5i1S6BKAJA==",
|
||||
"dependencies": {
|
||||
"axios": "^0.26.0",
|
||||
"form-data": "^4.0.0"
|
||||
"@types/node": "^18.11.18",
|
||||
"@types/node-fetch": "^2.6.4",
|
||||
"abort-controller": "^3.0.0",
|
||||
"agentkeepalive": "^4.2.1",
|
||||
"digest-fetch": "^1.3.0",
|
||||
"form-data-encoder": "1.7.2",
|
||||
"formdata-node": "^4.3.2",
|
||||
"node-fetch": "^2.6.7",
|
||||
"web-streams-polyfill": "^3.2.1"
|
||||
},
|
||||
"bin": {
|
||||
"openai": "bin/cli"
|
||||
}
|
||||
},
|
||||
"node_modules/openai-old": {
|
||||
"name": "openai",
|
||||
"version": "3.3.0",
|
||||
"license": "MIT",
|
||||
"node_modules/openai/node_modules/@types/node": {
|
||||
"version": "18.18.13",
|
||||
"resolved": "https://registry.npmjs.org/@types/node/-/node-18.18.13.tgz",
|
||||
"integrity": "sha512-vXYZGRrSCreZmq1rEjMRLXJhiy8MrIeVasx+PCVlP414N7CJLHnMf+juVvjdprHyH+XRy3zKZLHeNueOpJCn0g==",
|
||||
"dependencies": {
|
||||
"axios": "^0.26.0",
|
||||
"form-data": "^4.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/openai-old/node_modules/axios": {
|
||||
"version": "0.26.1",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"follow-redirects": "^1.14.8"
|
||||
}
|
||||
},
|
||||
"node_modules/openai/node_modules/axios": {
|
||||
"version": "0.26.1",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"follow-redirects": "^1.14.8"
|
||||
"undici-types": "~5.26.4"
|
||||
}
|
||||
},
|
||||
"node_modules/openapi-fetch": {
|
||||
@@ -34939,7 +34855,7 @@
|
||||
"lottie-light-react": "^2.4.0",
|
||||
"lucide-react": "^0.167.0",
|
||||
"next-themes": "^0.2.1",
|
||||
"openai": "^3.3.0",
|
||||
"openai": "^4.17.0",
|
||||
"postcss": "^8.4.31",
|
||||
"prop-types": "^15.7.2",
|
||||
"react-copy-to-clipboard": "^5.1.0",
|
||||
|
||||
@@ -64,7 +64,7 @@
|
||||
"lottie-light-react": "^2.4.0",
|
||||
"lucide-react": "^0.167.0",
|
||||
"next-themes": "^0.2.1",
|
||||
"openai": "^3.3.0",
|
||||
"openai": "^4.17.0",
|
||||
"postcss": "^8.4.31",
|
||||
"prop-types": "^15.7.2",
|
||||
"react-copy-to-clipboard": "^5.1.0",
|
||||
|
||||
@@ -1,8 +1,4 @@
|
||||
import type {
|
||||
ChatCompletionResponseMessage,
|
||||
CreateChatCompletionResponse,
|
||||
CreateChatCompletionResponseChoicesInner,
|
||||
} from 'openai'
|
||||
import type OpenAI from 'openai'
|
||||
import {
|
||||
Dispatch,
|
||||
SetStateAction,
|
||||
@@ -24,15 +20,15 @@ import {
|
||||
Input,
|
||||
markdownComponents,
|
||||
} from 'ui'
|
||||
import { AiIcon, AiIconChat } from './Command.icons'
|
||||
import { AiIconChat } from './Command.icons'
|
||||
import { CommandGroup, CommandItem, useAutoInputFocus, useHistoryKeys } from './Command.utils'
|
||||
|
||||
import { AiWarning } from './Command.alerts'
|
||||
import { useCommandMenu } from './CommandMenuProvider'
|
||||
|
||||
import ReactMarkdown from 'react-markdown'
|
||||
import { cn } from './../../lib/utils'
|
||||
import remarkGfm from 'remark-gfm'
|
||||
import { cn } from './../../lib/utils'
|
||||
|
||||
const questions = [
|
||||
'How do I get started with Supabase?',
|
||||
@@ -43,13 +39,6 @@ const questions = [
|
||||
'How do I set up authentication?',
|
||||
]
|
||||
|
||||
type CreateChatCompletionResponseChoicesInnerDelta = Omit<
|
||||
CreateChatCompletionResponseChoicesInner,
|
||||
'message'
|
||||
> & {
|
||||
delta: Partial<ChatCompletionResponseMessage>
|
||||
}
|
||||
|
||||
function getEdgeFunctionUrl() {
|
||||
const supabaseUrl = process.env.NEXT_PUBLIC_SUPABASE_URL?.replace(/\/$/, '')
|
||||
|
||||
@@ -236,12 +225,12 @@ export function useAiChat({
|
||||
|
||||
setIsResponding(true)
|
||||
|
||||
const completionResponse: CreateChatCompletionResponse = JSON.parse(e.data)
|
||||
const completionChunk: OpenAI.Chat.Completions.ChatCompletionChunk = JSON.parse(e.data)
|
||||
const [
|
||||
{
|
||||
delta: { content },
|
||||
},
|
||||
] = completionResponse.choices as CreateChatCompletionResponseChoicesInnerDelta[]
|
||||
] = completionChunk.choices
|
||||
|
||||
if (content) {
|
||||
dispatchMessage({
|
||||
@@ -328,12 +317,12 @@ export function queryAi(messages: Message[], timeout = 0) {
|
||||
return
|
||||
}
|
||||
|
||||
const completionResponse: CreateChatCompletionResponse = JSON.parse(e.data)
|
||||
const completionChunk: OpenAI.Chat.Completions.ChatCompletionChunk = JSON.parse(e.data)
|
||||
const [
|
||||
{
|
||||
delta: { content },
|
||||
},
|
||||
] = completionResponse.choices as CreateChatCompletionResponseChoicesInnerDelta[]
|
||||
] = completionChunk.choices
|
||||
|
||||
if (content) {
|
||||
answer += content
|
||||
|
||||
Reference in new issue
Block a user