kalhdrawi commited on
Commit
a51c5c9
·
1 Parent(s): 65ef364

Reupload OmniDev clean version

Browse files
app/api/me/projects/route.ts CHANGED
@@ -13,7 +13,7 @@ export async function POST(
13
  return NextResponse.json({ message: "Unauthorized" }, { status: 401 });
14
  }
15
 
16
- const { title: titleFromRequest, pages, prompt } = await req.json();
17
 
18
  const title = titleFromRequest ?? "DeepSite Project";
19
 
@@ -49,17 +49,26 @@ This project was created with [DeepSite](https://deepsite.hf.co).
49
  const files: File[] = [];
50
  const readmeFile = new File([README], "README.md", { type: "text/markdown" });
51
  files.push(readmeFile);
52
- pages.forEach((page: Page) => {
53
- const file = new File([page.html], page.path, { type: "text/html" });
54
- files.push(file);
55
- });
 
 
 
 
 
 
 
 
 
56
 
57
  try {
58
  const { repoUrl} = await createRepo({
59
  repo,
60
  accessToken: user.token as string,
61
  });
62
- const commitTitle = !prompt || prompt.trim() === "" ? "Redesign my website" : prompt;
63
  await uploadFiles({
64
  repo,
65
  files,
@@ -104,4 +113,4 @@ This project was created with [DeepSite](https://deepsite.hf.co).
104
  { status: 500 }
105
  );
106
  }
107
- }
 
13
  return NextResponse.json({ message: "Unauthorized" }, { status: 401 });
14
  }
15
 
16
+ const { title: titleFromRequest, pages, prompt, initialFiles } = await req.json();
17
 
18
  const title = titleFromRequest ?? "DeepSite Project";
19
 
 
49
  const files: File[] = [];
50
  const readmeFile = new File([README], "README.md", { type: "text/markdown" });
51
  files.push(readmeFile);
52
+ if (Array.isArray(pages)) {
53
+ pages.forEach((page: Page) => {
54
+ const file = new File([page.html], page.path, { type: "text/html" });
55
+ files.push(file);
56
+ });
57
+ }
58
+ if (Array.isArray(initialFiles)) {
59
+ initialFiles.forEach((f: { path: string; content: string; type?: string }) => {
60
+ const path = (f.path || '').replace(/^\/+/, '');
61
+ const type = f.type || (path.endsWith('.html') ? 'text/html' : path.endsWith('.json') ? 'application/json' : 'text/plain');
62
+ files.push(new File([f.content || ''], path, { type }));
63
+ });
64
+ }
65
 
66
  try {
67
  const { repoUrl} = await createRepo({
68
  repo,
69
  accessToken: user.token as string,
70
  });
71
+ const commitTitle = (!prompt || prompt.trim() === "") ? (Array.isArray(initialFiles) ? "OmniDev: Initialize project" : "Redesign my website") : prompt;
72
  await uploadFiles({
73
  repo,
74
  files,
 
113
  { status: 500 }
114
  );
115
  }
116
+ }
app/new/page.tsx CHANGED
@@ -1,6 +1,6 @@
1
- import { AppEditor } from "@/components/editor";
2
  import { Metadata } from "next";
3
  import { generateSEO } from "@/lib/seo";
 
4
 
5
  export const metadata: Metadata = generateSEO({
6
  title: "Create New Project - OmniDev",
@@ -10,5 +10,5 @@ export const metadata: Metadata = generateSEO({
10
  });
11
 
12
  export default function NewProjectPage() {
13
- return <AppEditor isNew />;
14
  }
 
 
1
  import { Metadata } from "next";
2
  import { generateSEO } from "@/lib/seo";
3
+ import ScaffoldNew from "@/components/new/scaffold";
4
 
5
  export const metadata: Metadata = generateSEO({
6
  title: "Create New Project - OmniDev",
 
10
  });
11
 
12
  export default function NewProjectPage() {
13
+ return <ScaffoldNew />;
14
  }
components/new/scaffold.tsx ADDED
@@ -0,0 +1,98 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ "use client";
2
+ import { useEffect, useState } from "react";
3
+ import { useUser } from "@/hooks/useUser";
4
+ import { useAi } from "@/hooks/useAi";
5
+ import { useRouter } from "next/navigation";
6
+ import { Button } from "@/components/ui/button";
7
+ import { toast } from "sonner";
8
+
9
+ const DEFAULT_INSTRUCTION = `Initialize a complete full-stack web project with the following structure and runnable code:
10
+
11
+ Requirements:
12
+ - Frontend under /frontend using React + Vite (JavaScript), TailwindCSS preconfigured.
13
+ - Backend under /backend using Express (JavaScript, ESM), with basic routes (GET /, GET /health) and CORS enabled.
14
+ - Add a minimal README.md at root.
15
+ - Provide package.json in both /frontend and /backend with scripts to start dev/prod.
16
+ - Provide /frontend/index.html and /frontend/src/main.jsx, /frontend/src/App.jsx.
17
+ - Provide /backend/server.js.
18
+ - Use ports 5173 for frontend and 3000 for backend.
19
+ - Keep everything simple and runnable.
20
+ - Return JSON strictly as file updates (no markdown), paths rooted from repo, e.g. /frontend/..., /backend/...`;
21
+
22
+ export default function ScaffoldNew() {
23
+ const { user, openLoginWindow } = useUser();
24
+ const { model, provider } = useAi();
25
+ const router = useRouter();
26
+ const [loading, setLoading] = useState(false);
27
+ const [error, setError] = useState<string | null>(null);
28
+ const [logs, setLogs] = useState<string[]>([]);
29
+
30
+ async function runScaffold() {
31
+ if (!user) {
32
+ await openLoginWindow();
33
+ return;
34
+ }
35
+ setLoading(true);
36
+ setError(null);
37
+ setLogs(["Starting scaffold via Augment..."]);
38
+ try {
39
+ // 1) Call augment to generate full-stack files
40
+ const aug = await fetch('/api/augment', {
41
+ method: 'POST',
42
+ headers: { 'Content-Type': 'application/json' },
43
+ body: JSON.stringify({
44
+ context: '/ (empty project)',
45
+ instruction: DEFAULT_INSTRUCTION,
46
+ language: 'javascript',
47
+ framework: 'express-react',
48
+ response_type: 'file_updates',
49
+ model,
50
+ provider,
51
+ }),
52
+ }).then(r => r.json());
53
+ if (!aug?.ok || !Array.isArray(aug.files) || aug.files.length === 0) {
54
+ throw new Error(aug?.message || 'Augment did not return files');
55
+ }
56
+ setLogs(prev => [...prev, `Augment produced ${aug.files.length} files`]);
57
+
58
+ // 2) Create space with initial files
59
+ const title = 'OmniDev Full-Stack Project';
60
+ const created = await fetch('/api/me/projects', {
61
+ method: 'POST',
62
+ headers: { 'Content-Type': 'application/json' },
63
+ body: JSON.stringify({ title, initialFiles: aug.files.map((f: any) => ({ path: f.path, content: f.content })) })
64
+ }).then(r => r.json());
65
+ if (!created?.space?.project?.space_id) {
66
+ throw new Error(created?.error || 'Failed to create project');
67
+ }
68
+ setLogs(prev => [...prev, 'Project created, redirecting...']);
69
+ router.push(`/${created.space.project.space_id}`);
70
+ } catch (e: any) {
71
+ setError(e?.message || 'Scaffold failed');
72
+ toast.error(e?.message || 'Scaffold failed');
73
+ } finally {
74
+ setLoading(false);
75
+ }
76
+ }
77
+
78
+ useEffect(() => {
79
+ // Auto-run once when visiting /new
80
+ runScaffold();
81
+ // eslint-disable-next-line react-hooks/exhaustive-deps
82
+ }, []);
83
+
84
+ return (
85
+ <section className="max-w-2xl mx-auto p-6 text-neutral-200">
86
+ <h1 className="text-2xl font-semibold mb-2">Initializing Full-Stack Project...</h1>
87
+ <p className="text-sm text-neutral-400 mb-4">OmniDev is generating a complete frontend + backend project. This may take a moment.</p>
88
+ {error && <p className="text-red-400 text-sm mb-2">{error}</p>}
89
+ <ul className="text-sm text-neutral-400 space-y-1">
90
+ {logs.map((l, i) => (<li key={i}>• {l}</li>))}
91
+ </ul>
92
+ <div className="mt-4">
93
+ <Button size="sm" onClick={runScaffold} disabled={loading}>{loading ? 'Working...' : 'Retry'}</Button>
94
+ </div>
95
+ </section>
96
+ );
97
+ }
98
+