Migrate Text-to-CAD (edit) to multi-file endpoint (#6066)

* start of migrate to multi file endpoint

* get some relative path stuff sorted

* blobifying files, and making selections work with imports working

* add write to disk

* warn about big projects

* update known circular

* update snapshot

* remove log

* tweak selection filters

* Update src/components/ModelingMachineProvider.tsx

Co-authored-by: graphite-app[bot] <96075541+graphite-app[bot]@users.noreply.github.com>

* fmt

* fix one thing

* typo

* raw dog form data like a fucking peasant

* remove fake data

* fmt

* steal Kevin's stuff

* good progress

* clean up

* fix writing to files when response returns

* comment the terriable code

* push fix of sorts

* better fix

* spot of clean up

* fix: Needed to support the bad request flow, the toast will hang forever, the return control flows don't dismiss a forever toast

* fix: handling more error flows by dismissing the toast

* chore: leaving a comment for a confusing workflow

* fix: trying to clean up some async logic

* fix: trying to fix a few things at once...

* fix: fixing toast success

* fix: how did this desync?

* fix: removing useless logic, we write to disk ahead of time, the continue is to say ya no problem

* fix: typo

* Change back to `spawnChild`, forego `actors` by reference

* fix: updating PR comments

* fix: found a bug with paths from rust! it is actually OS paths!

* fix: updated type still is failing tsc

* fix: the type of the machine was wrong, we always set it to at least ''

* fix: idk man

* Fix happy path test (button labels)

---------

Co-authored-by: graphite-app[bot] <96075541+graphite-app[bot]@users.noreply.github.com>
Co-authored-by: Kevin Nadro <kevin@zoo.dev>
Co-authored-by: Frank Noirot <frankjohnson1993@gmail.com>
Co-authored-by: Kevin Nadro <nadr0@users.noreply.github.com>
Co-authored-by: Pierre Jacquier <pierre@zoo.dev>
This commit is contained in:
Kurt Hutten
2025-05-08 03:54:40 +10:00
committed by GitHub
parent f938364d54
commit 43d5a72514
19 changed files with 931 additions and 307 deletions

View File

@ -1,6 +1,6 @@
import type {
TextToCadIteration_type,
TextToCad_type,
TextToCadMultiFileIteration_type,
} from '@kittycad/lib/dist/types/src/models'
import { useCallback, useEffect, useRef } from 'react'
import toast from 'react-hot-toast'
@ -29,9 +29,17 @@ import { PATHS } from '@src/lib/paths'
import { codeManager, kclManager, systemIOActor } from '@src/lib/singletons'
import { sendTelemetry } from '@src/lib/textToCadTelemetry'
import { reportRejection } from '@src/lib/trap'
import {
SystemIOMachineEvents,
waitForIdleState,
} from '@src/machines/systemIO/utils'
import {
useProjectDirectoryPath,
useRequestedProjectName,
} from '@src/machines/systemIO/hooks'
import { commandBarActor } from '@src/lib/singletons'
import { SystemIOMachineEvents } from '@src/machines/systemIO/utils'
import { useProjectDirectoryPath } from '@src/machines/systemIO/hooks'
import type { FileMeta } from '@src/lib/types'
import type { RequestedKCLFile } from '@src/machines/systemIO/utils'
const CANVAS_SIZE = 128
const PROMPT_TRUNCATE_LENGTH = 128
@ -478,14 +486,17 @@ export function ToastPromptToEditCadSuccess({
toastId,
token,
data,
oldCode,
oldCodeWebAppOnly: oldCode,
oldFiles,
}: {
toastId: string
oldCode: string
data: TextToCadIteration_type
oldCodeWebAppOnly: string
oldFiles: FileMeta[]
data: TextToCadMultiFileIteration_type
token?: string
}) {
const modelId = data.id
const requestedProjectName = useRequestedProjectName()
return (
<div className="flex gap-4 min-w-80">
@ -514,13 +525,37 @@ export function ToastPromptToEditCadSuccess({
data-negative-button={'reject'}
name={'Reject'}
onClick={() => {
sendTelemetry(modelId, 'rejected', token).catch(reportRejection)
codeManager.updateCodeEditor(oldCode)
kclManager.executeCode().catch(reportRejection)
toast.dismiss(toastId)
void (async () => {
sendTelemetry(modelId, 'rejected', token).catch(reportRejection)
// revert to before the prompt-to-edit
if (isDesktop()) {
const requestedFiles: RequestedKCLFile[] = []
for (const file of oldFiles) {
if (file.type !== 'kcl') {
// only need to write the kcl files
// as the endpoint would have never overwritten other file types
continue
}
requestedFiles.push({
requestedCode: file.fileContents,
requestedFileName: file.relPath,
requestedProjectName: requestedProjectName.name,
})
}
toast.dismiss(toastId)
await writeOverFilesAndExecute({
requestedFiles: requestedFiles,
projectName: requestedProjectName.name,
})
} else {
codeManager.updateCodeEditor(oldCode)
kclManager.executeCode().catch(reportRejection)
toast.dismiss(toastId)
}
})()
}}
>
{'Reject'}
{'Revert'}
</ActionButton>
<ActionButton
@ -532,23 +567,38 @@ export function ToastPromptToEditCadSuccess({
onClick={() => {
sendTelemetry(modelId, 'accepted', token).catch(reportRejection)
toast.dismiss(toastId)
// Write new content to disk since they have accepted.
codeManager
.writeToFile()
.then(() => {
// no-op
})
.catch((e) => {
console.error('Failed to save prompt-to-edit to disk')
console.error(e)
})
/**
* NO OP. Do not rewrite code to disk, we already do this ahead of time. This will dismiss the toast.
* All of the files were already written! Don't rewrite the current code editor.
* If this prompt to edit makes 5 new files, the code manager is only watching 1 of these files, why
* would it rewrite the current file selected when this is completed?
*/
}}
>
Accept
Continue
</ActionButton>
</div>
</div>
</div>
)
}
export const writeOverFilesAndExecute = async ({
requestedFiles,
projectName,
}: {
requestedFiles: RequestedKCLFile[]
projectName: string
}) => {
systemIOActor.send({
type: SystemIOMachineEvents.bulkCreateKCLFilesAndNavigateToProject,
data: {
files: requestedFiles,
requestedProjectName: projectName,
override: true,
},
})
// to await the result of the send event above
await waitForIdleState({ systemIOActor })
}