claudeship 0.2.9 → 0.2.11
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/apps/server/dist/chat/prompts/fullstack-express-prompt.d.ts +1 -1
- package/apps/server/dist/chat/prompts/fullstack-express-prompt.js +16 -0
- package/apps/server/dist/chat/prompts/fullstack-express-prompt.js.map +1 -1
- package/apps/server/dist/chat/prompts/fullstack-fastapi-prompt.d.ts +1 -1
- package/apps/server/dist/chat/prompts/fullstack-fastapi-prompt.js +16 -0
- package/apps/server/dist/chat/prompts/fullstack-fastapi-prompt.js.map +1 -1
- package/apps/server/dist/chat/prompts/web-system-prompt.d.ts +1 -1
- package/apps/server/dist/chat/prompts/web-system-prompt.js +15 -0
- package/apps/server/dist/chat/prompts/web-system-prompt.js.map +1 -1
- package/apps/server/dist/preview/preview.controller.d.ts +1 -0
- package/apps/server/dist/preview/preview.controller.js +10 -0
- package/apps/server/dist/preview/preview.controller.js.map +1 -1
- package/apps/server/dist/preview/preview.service.d.ts +1 -0
- package/apps/server/dist/preview/preview.service.js +26 -2
- package/apps/server/dist/preview/preview.service.js.map +1 -1
- package/apps/server/dist/tsconfig.tsbuildinfo +1 -1
- package/apps/server/package.json +1 -1
- package/apps/web/.next/BUILD_ID +1 -1
- package/apps/web/.next/app-build-manifest.json +2 -2
- package/apps/web/.next/build-manifest.json +2 -2
- package/apps/web/.next/cache/.previewinfo +1 -1
- package/apps/web/.next/cache/.rscinfo +1 -1
- package/apps/web/.next/cache/.tsbuildinfo +1 -1
- package/apps/web/.next/cache/config.json +3 -3
- package/apps/web/.next/cache/eslint/.cache_j3uhuz +1 -1
- package/apps/web/.next/cache/webpack/client-production/0.pack +0 -0
- package/apps/web/.next/cache/webpack/client-production/index.pack +0 -0
- package/apps/web/.next/cache/webpack/edge-server-production/index.pack +0 -0
- package/apps/web/.next/cache/webpack/server-production/0.pack +0 -0
- package/apps/web/.next/cache/webpack/server-production/index.pack +0 -0
- package/apps/web/.next/prerender-manifest.json +10 -10
- package/apps/web/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
- package/apps/web/.next/server/app/_not-found.html +1 -1
- package/apps/web/.next/server/app/_not-found.rsc +1 -1
- package/apps/web/.next/server/app/index.html +1 -1
- package/apps/web/.next/server/app/index.rsc +1 -1
- package/apps/web/.next/server/app/page_client-reference-manifest.js +1 -1
- package/apps/web/.next/server/app/project/[id]/page.js +2 -2
- package/apps/web/.next/server/app/project/[id]/page_client-reference-manifest.js +1 -1
- package/apps/web/.next/server/app/settings/page_client-reference-manifest.js +1 -1
- package/apps/web/.next/server/app/settings.html +1 -1
- package/apps/web/.next/server/app/settings.rsc +1 -1
- package/apps/web/.next/server/pages/404.html +1 -1
- package/apps/web/.next/server/pages/500.html +1 -1
- package/apps/web/.next/server/server-reference-manifest.json +1 -1
- package/apps/web/.next/static/chunks/298-6f3d6b321c288cd3.js +1 -0
- package/apps/web/.next/static/chunks/app/project/[id]/page-e5cda6f9050b0a52.js +1 -0
- package/apps/web/.next/trace +17 -17
- package/apps/web/package.json +1 -1
- package/apps/web/src/components/preview/PreviewPanel.tsx +16 -1
- package/apps/web/src/components/workspace/WorkspaceLayout.tsx +5 -5
- package/apps/web/src/stores/useChatStore.ts +34 -9
- package/apps/web/src/stores/usePreviewStore.ts +22 -0
- package/package.json +1 -1
- package/apps/web/.next/static/chunks/595-00a84eeccb7bfc27.js +0 -1
- package/apps/web/.next/static/chunks/app/project/[id]/page-4c15c33bf78552cb.js +0 -1
- /package/apps/web/.next/static/{yVw9J0lkf1zLx2qq5O3Tu → zw4FcukMOho6_dzgpEdNW}/_buildManifest.js +0 -0
- /package/apps/web/.next/static/{yVw9J0lkf1zLx2qq5O3Tu → zw4FcukMOho6_dzgpEdNW}/_ssgManifest.js +0 -0
package/apps/web/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
|
|
3
3
|
import { useEffect, useState, useRef, useCallback } from "react";
|
|
4
|
-
import { Play, Square, RefreshCw, ExternalLink, Package, Loader2, Zap } from "lucide-react";
|
|
4
|
+
import { Play, Square, RefreshCw, ExternalLink, Package, Loader2, Zap, RotateCcw } from "lucide-react";
|
|
5
5
|
import { Button } from "@/components/ui/button";
|
|
6
6
|
import { usePreviewStore } from "@/stores/usePreviewStore";
|
|
7
7
|
import { useTranslation } from "@/lib/i18n";
|
|
@@ -27,6 +27,7 @@ export function PreviewPanel({ projectId }: PreviewPanelProps) {
|
|
|
27
27
|
projectReady,
|
|
28
28
|
startPreview,
|
|
29
29
|
stopPreview,
|
|
30
|
+
restartPreview,
|
|
30
31
|
refreshPreview,
|
|
31
32
|
fetchStatus,
|
|
32
33
|
checkProjectReady,
|
|
@@ -187,6 +188,7 @@ export function PreviewPanel({ projectId }: PreviewPanelProps) {
|
|
|
187
188
|
|
|
188
189
|
const handleStart = () => startPreview(projectId);
|
|
189
190
|
const handleStop = () => stopPreview(projectId);
|
|
191
|
+
const handleRestart = () => restartPreview(projectId);
|
|
190
192
|
const handleRefresh = () => refreshPreview();
|
|
191
193
|
const handleOpenExternal = () => {
|
|
192
194
|
if (url) {
|
|
@@ -243,14 +245,26 @@ export function PreviewPanel({ projectId }: PreviewPanelProps) {
|
|
|
243
245
|
onClick={handleRefresh}
|
|
244
246
|
disabled={isLoading}
|
|
245
247
|
className="h-8 w-8 p-0"
|
|
248
|
+
title="Refresh"
|
|
246
249
|
>
|
|
247
250
|
<RefreshCw className="h-4 w-4" />
|
|
248
251
|
</Button>
|
|
252
|
+
<Button
|
|
253
|
+
variant="ghost"
|
|
254
|
+
size="sm"
|
|
255
|
+
onClick={handleRestart}
|
|
256
|
+
disabled={isLoading}
|
|
257
|
+
className="h-8 w-8 p-0"
|
|
258
|
+
title="Restart server"
|
|
259
|
+
>
|
|
260
|
+
<RotateCcw className="h-4 w-4" />
|
|
261
|
+
</Button>
|
|
249
262
|
<Button
|
|
250
263
|
variant="ghost"
|
|
251
264
|
size="sm"
|
|
252
265
|
onClick={handleOpenExternal}
|
|
253
266
|
className="h-8 w-8 p-0"
|
|
267
|
+
title="Open in new tab"
|
|
254
268
|
>
|
|
255
269
|
<ExternalLink className="h-4 w-4" />
|
|
256
270
|
</Button>
|
|
@@ -260,6 +274,7 @@ export function PreviewPanel({ projectId }: PreviewPanelProps) {
|
|
|
260
274
|
onClick={handleStop}
|
|
261
275
|
disabled={isLoading}
|
|
262
276
|
className="h-8 w-8 p-0"
|
|
277
|
+
title="Stop"
|
|
263
278
|
>
|
|
264
279
|
<Square className="h-4 w-4" />
|
|
265
280
|
</Button>
|
|
@@ -57,18 +57,18 @@ export function WorkspaceLayout({ projectId }: WorkspaceLayoutProps) {
|
|
|
57
57
|
</div>
|
|
58
58
|
)}
|
|
59
59
|
|
|
60
|
-
{/* Chat Panel */}
|
|
60
|
+
{/* Chat Panel - 30% width */}
|
|
61
61
|
<div
|
|
62
|
-
className="border-r flex-
|
|
63
|
-
style={{
|
|
62
|
+
className="border-r flex-shrink-0"
|
|
63
|
+
style={{ width: showFileExplorer ? "calc(30% - 8rem)" : "30%" }}
|
|
64
64
|
>
|
|
65
65
|
<ChatPanel projectId={projectId} />
|
|
66
66
|
</div>
|
|
67
67
|
|
|
68
|
-
{/* Preview Panel */}
|
|
68
|
+
{/* Preview Panel - 70% width */}
|
|
69
69
|
<div
|
|
70
70
|
className="flex-1"
|
|
71
|
-
style={{
|
|
71
|
+
style={{ width: showFileExplorer ? "calc(70%)" : "70%" }}
|
|
72
72
|
>
|
|
73
73
|
<PreviewPanel projectId={projectId} />
|
|
74
74
|
</div>
|
|
@@ -1,6 +1,12 @@
|
|
|
1
1
|
import { create } from "zustand";
|
|
2
2
|
import { api, type UploadedFile } from "@/lib/api";
|
|
3
3
|
import { Role, type ChatMessage, type StreamEvent, type ChatMode, type AskUserQuestionData } from "@claudeship/shared";
|
|
4
|
+
import { usePreviewStore } from "./usePreviewStore";
|
|
5
|
+
|
|
6
|
+
// Marker detection constants
|
|
7
|
+
const RESTART_MARKER_REGEX = /<restart-preview\s*\/>/g;
|
|
8
|
+
const RESTART_DEBOUNCE_MS = 3000;
|
|
9
|
+
let lastRestartTime = 0;
|
|
4
10
|
|
|
5
11
|
export interface AttachedFile {
|
|
6
12
|
id: string;
|
|
@@ -452,15 +458,34 @@ export const useChatStore = create<ChatState>((set, get) => ({
|
|
|
452
458
|
console.log("[SSE Event]", data.type, data);
|
|
453
459
|
|
|
454
460
|
if (data.type === "text" && data.content) {
|
|
455
|
-
//
|
|
456
|
-
const
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
461
|
+
// Check for restart-preview marker
|
|
462
|
+
const hasRestartMarker = RESTART_MARKER_REGEX.test(data.content);
|
|
463
|
+
// Reset regex lastIndex after test()
|
|
464
|
+
RESTART_MARKER_REGEX.lastIndex = 0;
|
|
465
|
+
|
|
466
|
+
// Filter out the marker from content
|
|
467
|
+
const filteredContent = data.content.replace(RESTART_MARKER_REGEX, '').trim();
|
|
468
|
+
|
|
469
|
+
// Trigger preview restart with debouncing
|
|
470
|
+
if (hasRestartMarker) {
|
|
471
|
+
const now = Date.now();
|
|
472
|
+
if (now - lastRestartTime > RESTART_DEBOUNCE_MS) {
|
|
473
|
+
lastRestartTime = now;
|
|
474
|
+
usePreviewStore.getState().restartPreview(projectId);
|
|
475
|
+
}
|
|
476
|
+
}
|
|
477
|
+
|
|
478
|
+
// Only add text block if there's content after filtering
|
|
479
|
+
if (filteredContent) {
|
|
480
|
+
const textBlock: StreamingBlock = {
|
|
481
|
+
id: `text-${Date.now()}-${Math.random().toString(36).substr(2, 9)}`,
|
|
482
|
+
type: "text",
|
|
483
|
+
content: filteredContent,
|
|
484
|
+
};
|
|
485
|
+
set((state) => ({
|
|
486
|
+
streamingBlocks: [...state.streamingBlocks, textBlock],
|
|
487
|
+
}));
|
|
488
|
+
}
|
|
464
489
|
} else if (data.type === "tool_use" && data.tool) {
|
|
465
490
|
// Add tool_use block
|
|
466
491
|
const toolBlock: StreamingBlock = {
|
|
@@ -36,6 +36,7 @@ interface PreviewState {
|
|
|
36
36
|
|
|
37
37
|
startPreview: (projectId: string) => Promise<void>;
|
|
38
38
|
stopPreview: (projectId: string) => Promise<void>;
|
|
39
|
+
restartPreview: (projectId: string) => Promise<void>;
|
|
39
40
|
refreshPreview: () => void;
|
|
40
41
|
fetchStatus: (projectId: string) => Promise<void>;
|
|
41
42
|
checkProjectReady: (projectId: string) => Promise<void>;
|
|
@@ -92,6 +93,27 @@ export const usePreviewStore = create<PreviewState>((set, get) => ({
|
|
|
92
93
|
}
|
|
93
94
|
},
|
|
94
95
|
|
|
96
|
+
restartPreview: async (projectId: string) => {
|
|
97
|
+
set({ isLoading: true, error: null, status: "starting" });
|
|
98
|
+
try {
|
|
99
|
+
const result = await api.post<PreviewStatus>(
|
|
100
|
+
`/projects/${projectId}/preview/restart`
|
|
101
|
+
);
|
|
102
|
+
set({
|
|
103
|
+
status: result.status,
|
|
104
|
+
url: result.url || null,
|
|
105
|
+
isLoading: false,
|
|
106
|
+
});
|
|
107
|
+
} catch (error) {
|
|
108
|
+
set({
|
|
109
|
+
error:
|
|
110
|
+
error instanceof Error ? error.message : "Failed to restart preview",
|
|
111
|
+
status: "error",
|
|
112
|
+
isLoading: false,
|
|
113
|
+
});
|
|
114
|
+
}
|
|
115
|
+
},
|
|
116
|
+
|
|
95
117
|
refreshPreview: () => {
|
|
96
118
|
const currentUrl = get().url;
|
|
97
119
|
if (currentUrl) {
|