From 1b99f59f2c9e1c9db97fe59f5a40edea9ee99ef0 Mon Sep 17 00:00:00 2001 From: florianbgt Date: Wed, 18 Jun 2025 16:43:55 +0200 Subject: [PATCH 1/3] implement bucket --- .github/workflows/test-lint.yml | 7 ++ deno.json | 5 +- packages/app/src/pages/projects/add.tsx | 25 +++++++ .../projects/project/manifests/manifest.tsx | 22 ++++-- .../src/pages/projects/project/settings.tsx | 26 +++++++ packages/core/deno.json | 1 + packages/core/src/api/manifest/router.test.ts | 30 +++++++- packages/core/src/api/manifest/service.ts | 23 +++++- packages/core/src/api/project/router.test.ts | 30 ++++++++ packages/core/src/api/project/router.ts | 2 + packages/core/src/api/project/service.ts | 4 ++ packages/core/src/api/project/types.ts | 2 + packages/core/src/bucketStorage/index.ts | 72 +++++++++++++++++++ .../core/src/db/migrations/0001.migration.ts | 4 +- .../core/src/db/migrations/0002.migration.ts | 17 ----- packages/core/src/db/models/manifest.ts | 2 +- packages/core/src/db/models/project.ts | 1 + packages/core/src/settings.ts | 6 ++ 18 files changed, 249 insertions(+), 30 deletions(-) create mode 100644 packages/core/src/bucketStorage/index.ts delete mode 100644 packages/core/src/db/migrations/0002.migration.ts diff --git a/.github/workflows/test-lint.yml b/.github/workflows/test-lint.yml index 834ace4..67a9fba 100644 --- a/.github/workflows/test-lint.yml +++ b/.github/workflows/test-lint.yml @@ -40,6 +40,13 @@ jobs: ports: - 12111:12111 - 12112:12112 + fake-gcs-server: + image: fsouza/fake-gcs-server:latest + ports: + - 4443:4443 + options: >- + --scheme http + --public-host localhost:4443 steps: - name: Checkout repository uses: actions/checkout@v4 diff --git a/deno.json b/deno.json index e43e3fc..c82e4b8 100644 --- a/deno.json +++ b/deno.json @@ -11,13 +11,14 @@ "dev:runner": "deno task --config ./packages/runner/deno.json dev", "build:app": "deno task --config ./packages/app/deno.json build", "build:core": "deno task --config ./packages/core/deno.json build", - "test": "STRIPE_USE_MOCK=true deno test -A", + "test": "STRIPE_USE_MOCK=true GCP_USE_FAKE_GCS_SERVER=true deno test -A", "db:docker": "docker container rm stackcore-pg --force || true && docker run --name stackcore-pg -e POSTGRES_PASSWORD=password -e POSTGRES_USER=user -e POSTGRES_DB=core -p 5432:5432 -d postgres:17", "db:migrate": "deno task --config ./packages/core/deno.json migrate -A", "stripe:create-products": "deno run -A --env-file=.env ./packages/core/src/stripe/scripts/createProducts.ts", "stripe:cli": "docker run --rm -it --env-file=.env stripe/stripe-cli:latest", "stripe:forward": "deno task stripe:cli listen --forward-to http://host.docker.internal:4000/billing/webhook", - "stripe:mock": "docker run --rm -it -p 12111-12112:12111-12112 stripe/stripe-mock:latest" + "stripe:mock": "docker run --rm -it -p 12111-12112:12111-12112 stripe/stripe-mock:latest", + "bucket:mock": "docker run --rm -it -p 4443:4443 fsouza/fake-gcs-server:latest -scheme http -public-host localhost:4443" }, "lint": { "exclude": [ diff --git a/packages/app/src/pages/projects/add.tsx b/packages/app/src/pages/projects/add.tsx index 4f1598e..e1f0819 100644 --- a/packages/app/src/pages/projects/add.tsx +++ b/packages/app/src/pages/projects/add.tsx @@ -47,6 +47,7 @@ export default function AddProjectPage() { const formSchema = z.object({ name: z.string().min(1, "Project name is required").max(100), + repoUrl: z.string().url("Invalid repository URL"), maxCodeCharPerSymbol: z.number().int().min(1, "Must be at least 1"), maxCodeCharPerFile: z.number().int().min(1, "Must be at least 1"), maxCharPerSymbol: z.number().int().min(1, "Must be at least 1"), @@ -74,6 +75,7 @@ export default function AddProjectPage() { disabled: isBusy, defaultValues: { name: "", + repoUrl: "", maxCodeCharPerSymbol: 1000, maxCodeCharPerFile: 50000, maxCharPerSymbol: 2000, @@ -102,6 +104,7 @@ export default function AddProjectPage() { try { const { url, method, body } = ProjectApiTypes.prepareCreateProject({ name: values.name, + repoUrl: values.repoUrl, workspaceId: selectedWorkspaceId, maxCodeCharPerSymbol: values.maxCodeCharPerSymbol, maxCodeCharPerFile: values.maxCodeCharPerFile, @@ -325,6 +328,28 @@ export default function AddProjectPage() { )} /> + ( + + + Repository URL{" "} + * + + + + + + The URL of the repository for this project + + + + )} + /> {/* Configuration Tabs */} diff --git a/packages/app/src/pages/projects/project/manifests/manifest.tsx b/packages/app/src/pages/projects/project/manifests/manifest.tsx index 192c6d6..e66f1fa 100644 --- a/packages/app/src/pages/projects/project/manifests/manifest.tsx +++ b/packages/app/src/pages/projects/project/manifests/manifest.tsx @@ -21,7 +21,7 @@ export default function ProjectManifest() { ManifestApiTypes.GetManifestDetailsResponse | undefined >(undefined); - const [_dependencyManifest, setDependencyManifest] = useState< + const [dependencyManifest, setDependencyManifest] = useState< DependencyManifest | undefined >(undefined); @@ -29,6 +29,17 @@ export default function ProjectManifest() { ManifestApiTypes.GetManifestAuditResponse | undefined >(undefined); + async function fetchManifest(url: string) { + const response = await fetch(url); + if (!response.ok) { + throw new Error("Failed to fetch manifest"); + } + const manifest = await response + .json() as unknown as DependencyManifest; + + return manifest; + } + useEffect(() => { async function fetchData() { if (!manifestId) { @@ -53,9 +64,12 @@ export default function ProjectManifest() { throw new Error("Failed to fetch manifest"); } - const manifest = await manifestResponse.json(); + const manifest = await manifestResponse + .json() as ManifestApiTypes.GetManifestDetailsResponse; setManifestData(manifest); - setDependencyManifest(manifest.manifest); + + const dependencyManifest = await fetchManifest(manifest.manifest); + setDependencyManifest(dependencyManifest); // Fetch audit manifest const { url: auditUrl, method: auditMethod } = ManifestApiTypes @@ -93,7 +107,7 @@ export default function ProjectManifest() { return ( ); diff --git a/packages/app/src/pages/projects/project/settings.tsx b/packages/app/src/pages/projects/project/settings.tsx index 0b81552..d666d6a 100644 --- a/packages/app/src/pages/projects/project/settings.tsx +++ b/packages/app/src/pages/projects/project/settings.tsx @@ -46,6 +46,7 @@ export default function ProjectSettings() { const formSchema = z.object({ name: z.string().min(1, "Project name is required").max(100), + repoUrl: z.string().url("Invalid repository URL"), maxCodeCharPerSymbol: z.number().int().min(1, "Must be at least 1"), maxCodeCharPerFile: z.number().int().min(1, "Must be at least 1"), maxCharPerSymbol: z.number().int().min(1, "Must be at least 1"), @@ -73,6 +74,7 @@ export default function ProjectSettings() { disabled: isBusy, defaultValues: { name: context.project.name, + repoUrl: context.project.repo_url, maxCodeCharPerSymbol: context.project.max_code_char_per_symbol, maxCodeCharPerFile: context.project.max_code_char_per_file, maxCharPerSymbol: context.project.max_char_per_symbol, @@ -100,6 +102,7 @@ export default function ProjectSettings() { context.project.id, { name: values.name, + repoUrl: values.repoUrl, maxCodeCharPerSymbol: values.maxCodeCharPerSymbol, maxCodeCharPerFile: values.maxCodeCharPerFile, maxCharPerSymbol: values.maxCharPerSymbol, @@ -298,6 +301,28 @@ export default function ProjectSettings() { )} /> + ( + + + Repository URL{" "} + * + + + + + + The URL of the repository for this project + + + + )} + /> {/* Configuration Tabs */} @@ -380,6 +405,7 @@ export default function ProjectSettings() {