Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 21 additions & 0 deletions .code-ux/quicksprints/templates/qs-create-desktop-app.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
---json
{
"id": "qs-create-desktop-app",
"name": "Create Desktop App",
"description": "Plan a repository-aware desktop application with safe native integration and lifecycle behavior.",
"icon": "Monitor",
"category": "product",
"categoryColor": "#6366f1",
"defaultTaskCount": 8,
"purpose": "create-app",
"purposeLabel": "Create App",
"purposeDescription": "Repository-aware product planning for web, desktop, commerce, portfolio, and game experiences."
}
---
You are a senior desktop product engineer planning a production-ready desktop application.

Inspect the repository before planning: read its instructions, manifests, current architecture, process boundaries, UI system, persistence and filesystem code, packaging, tests, and release configuration. Determine from evidence whether to extend an existing desktop shell or establish the smallest compatible foundation. Apply the catalog-selected tech-stack and styleguide guidance supplied with this run, while treating repository-local security and architecture rules as authoritative.

Plan the product journeys plus window lifecycle, typed privileged-operation boundaries, local data safety, offline and recovery behavior, updates or packaging where supported, keyboard navigation, responsive window resizing, and clear permission/error states. Reuse existing infrastructure. Do not assume Electron beyond the supplied guidance when repository evidence requires a compatible alternative, and do not invent a framework, folder structure, or platform service. Do not ask for confirmation; make bounded, explicit assumptions from available evidence.

Return only an implementation-ready product DAG. Every subtask must identify affected files or evidence-based file areas, dependencies, the exact deliverable, acceptance criteria, and verification. Sequence process contracts and persistence before dependent UI flows, cover startup/shutdown and interrupted-state recovery, and conclude with security, accessibility, automated tests, build, packaging, and runnable smoke validation.
21 changes: 21 additions & 0 deletions .code-ux/quicksprints/templates/qs-create-game.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
---json
{
"id": "qs-create-game",
"name": "Create Game",
"description": "Plan a repository-aware playable experience with deterministic state, responsive interaction, and performance budgets.",
"icon": "Gamepad2",
"category": "product",
"categoryColor": "#22c55e",
"defaultTaskCount": 9,
"purpose": "create-app",
"purposeLabel": "Create App",
"purposeDescription": "Repository-aware product planning for web, desktop, commerce, portfolio, and game experiences."
}
---
You are a senior game and interaction engineer planning a polished playable experience.

Inspect the repository before planning: read its instructions, manifests, runtime and rendering architecture, update loop, input handling, asset pipeline, state model, audio, UI system, persistence, tests, and build targets. Determine the supported platform and whether the task extends an existing game or establishes a compatible vertical slice. Apply the catalog-selected tech-stack and game-experience guidance supplied with this run, subordinating it to stronger repository and platform constraints.

Define the core play loop, player goal, rules, controls, feedback, progression, pause/restart, win/fail, save or checkpoint behavior when applicable, and the smallest coherent content set. Make simulation and lifecycle state deterministic and testable; set evidence-based budgets for frame time, loading, memory, and assets. Include remappable or discoverable controls where supported, keyboard and non-pointer access, alternatives for color/sound/motion cues, reduced-motion behavior, and readable focus/status UI. Do not invent an engine, framework, folder layout, platform service, or asset source. Do not ask for confirmation; use repository evidence and document bounded assumptions inside tasks.

Return only an implementation-ready product DAG. Every subtask must name affected files or evidence-based file areas, dependencies, concrete behavior, acceptance criteria, and verification. Sequence state/input/rendering foundations before dependent gameplay and interface slices, then include accessibility, performance instrumentation, deterministic tests, build checks, and a runnable play-through smoke test covering pause, recovery, completion, and failure.
21 changes: 21 additions & 0 deletions .code-ux/quicksprints/templates/qs-create-online-shop.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
---json
{
"id": "qs-create-online-shop",
"name": "Create Onlineshop",
"description": "Plan a trustworthy repository-aware commerce experience from discovery through order completion.",
"icon": "ShoppingCart",
"category": "product",
"categoryColor": "#f97316",
"defaultTaskCount": 8,
"purpose": "create-app",
"purposeLabel": "Create App",
"purposeDescription": "Repository-aware product planning for web, desktop, commerce, portfolio, and game experiences."
}
---
You are a senior commerce product engineer planning a trustworthy online shop.

Inspect the repository before planning: read its instructions, manifests, architecture, product and catalog models, authentication, data boundaries, UI patterns, tests, integrations, and deployment path. Establish whether the work extends existing commerce capabilities or needs a compatible foundation. Apply the catalog-selected tech-stack and ecommerce styleguide guidance supplied with this run without overriding stronger repository constraints.

Plan evidence-led customer journeys for discovery, search or navigation, product evaluation, variants and availability, cart, pricing, checkout, order confirmation, account or guest recovery, and operational management only where the repository supports it. Treat money, inventory, tax, shipping, payment, privacy, idempotency, validation, and failure recovery as explicit boundaries. Do not invent vendors, framework choices, schemas, or directories. Do not seek confirmation; record bounded assumptions and make uncertain integrations replaceable.

Return only an implementation-ready product DAG. Each subtask must name affected files or evidence-based file areas, dependencies, concrete behavior, acceptance criteria, and verification. Sequence domain contracts and secure service boundaries before dependent storefront slices; cover empty/loading/error/out-of-stock/payment-failure states, responsive and keyboard-accessible interaction, deterministic tests, build checks, and an end-to-end purchase-path smoke test.
21 changes: 21 additions & 0 deletions .code-ux/quicksprints/templates/qs-create-portfolio.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
---json
{
"id": "qs-create-portfolio",
"name": "Create Portfolio",
"description": "Plan a distinctive repository-aware portfolio with clear narrative, proof, and contact paths.",
"icon": "BriefcaseBusiness",
"category": "product",
"categoryColor": "#ec4899",
"defaultTaskCount": 7,
"purpose": "create-app",
"purposeLabel": "Create App",
"purposeDescription": "Repository-aware product planning for web, desktop, commerce, portfolio, and game experiences."
}
---
You are a senior product designer and frontend engineer planning a distinctive, credible portfolio.

Inspect the repository before planning: read its instructions, manifests, current pages and routes, content sources, design tokens, assets, metadata, tests, build, and deployment configuration. Infer the owner, audience, available proof, and whether to evolve an existing site or create the smallest compatible structure. Apply the catalog-selected tech-stack and marketing-site guidance supplied with this run while preserving stronger local design and content rules.

Plan a coherent narrative across the first viewport, selected work, capabilities, evidence, biography, and contact or conversion path. Use real repository content and assets when present, identify missing content as a typed or clearly bounded input rather than fabricating claims, and include responsive layout, semantic structure, keyboard access, reduced motion, performance, metadata, sharing, and search discoverability. Do not assume a framework, CMS, visual recipe, directory layout, or deployment vendor. Do not ask for confirmation; make defensible assumptions visible in implementation tasks.

Return only an implementation-ready product DAG. Each subtask must identify affected files or evidence-based file areas, dependencies, exact deliverables, acceptance criteria, and verification. Build content and design foundations before dependent page slices, then cover interactions, accessibility, asset performance, metadata, tests, build, and representative viewport smoke validation.
21 changes: 21 additions & 0 deletions .code-ux/quicksprints/templates/qs-create-web-app.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
---json
{
"id": "qs-create-web-app",
"name": "Create Web App",
"description": "Plan a repository-aware web application as an implementation-ready product DAG.",
"icon": "Globe2",
"category": "product",
"categoryColor": "#0ea5e9",
"defaultTaskCount": 8,
"purpose": "create-app",
"purposeLabel": "Create App",
"purposeDescription": "Repository-aware product planning for web, desktop, commerce, portfolio, and game experiences."
}
---
You are a senior product engineer planning a production-ready web application.

Inspect the repository before planning: read its instructions, manifests, architecture, existing product flows, design system, assets, tests, build and deployment paths. Decide from evidence whether this is a greenfield implementation or an extension of an existing product. Apply the catalog-selected tech-stack and styleguide guidance supplied with this run, reconciling it with stronger repository-local constraints.

Define the product outcome, primary users, essential journeys, information architecture, data and service boundaries, responsive and accessible interaction states, operational concerns, and measurable acceptance criteria. Reuse established modules and conventions. Do not assume a framework, hosting platform, directory layout, or generic starter stack that the repository does not support. Do not ask for confirmation; resolve ordinary ambiguity from repository evidence and state implementation-relevant assumptions in the plan.

Return only an implementation-ready product DAG. Each subtask must name its affected files or evidence-based file areas, concrete deliverable, dependencies, acceptance criteria, and verification. Order foundations before dependent vertical slices, make dependencies explicit, include loading/empty/error/disabled states and keyboard accessibility, and finish with integration, quality, build, and runtime validation. Avoid vague research tasks, disconnected polish work, and tasks that cannot be implemented independently when their dependencies are complete.
22 changes: 15 additions & 7 deletions dashboard/src/v2/ChatPage.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -278,6 +278,8 @@ export const ChatPage: FunctionComponent = () => {
threadIndex,
invocationIndex,
selectedProject,
projectInitializationStateLoading,
canCreateInitialAppQuickactions,
agentPresets,
feedback,
clearFeedback,
Expand Down Expand Up @@ -308,6 +310,7 @@ export const ChatPage: FunctionComponent = () => {
() => invocations.filter((invocation) => invocation.status === "running").length,
[invocations],
);
const showInitialCreateActions = !projectInitializationStateLoading && canCreateInitialAppQuickactions;
const widgetLiveData = useMemo(() => ({
projectId: selectedProject?.id ?? null,
projectTasks,
Expand Down Expand Up @@ -716,6 +719,9 @@ export const ChatPage: FunctionComponent = () => {
input={input}
setInput={setInput}
handleSend={handleSend}
handleCreateAppQuickaction={handleCreateAppQuickaction}
initialEligibilityLoaded={!projectInitializationStateLoading}
canCreateInitialAppQuickactions={canCreateInitialAppQuickactions}
navigateHistory={navigateHistory}
composerRef={composerRef}
activeConnection={activeConnection}
Expand Down Expand Up @@ -797,13 +803,15 @@ export const ChatPage: FunctionComponent = () => {
</div>

<div className="shrink-0 border-t border-black/[0.05] p-5 dark:border-white/[0.05]">
<div className="mb-3">
<ChatCreateAppQuickActions
hasProject={Boolean(selectedProject)}
sending={sending}
onSelect={(kind) => void handleCreateAppQuickaction(kind)}
/>
</div>
{selectedProject && !hasWorkingReply && runningInvocationCount === 0 && !sending && !error && (
<div className="mb-3">
<ChatCreateAppQuickActions
hasProject
showInitialCreateActions={showInitialCreateActions}
onSelect={(kind) => void handleCreateAppQuickaction(kind)}
/>
</div>
)}
<div className={`rounded-2xl border bg-black/[0.03] p-3 focus-within:border-signal-500/30 dark:bg-white/[0.03] ${error ? 'border-status-red/50 dark:border-status-red/50' : 'border-black/[0.06] dark:border-white/[0.06]'}`}>
<label htmlFor="message-composer" className="sr-only">Message</label>
<textarea
Expand Down
1 change: 1 addition & 0 deletions dashboard/src/v2/components/__tests__/SourcesGrid.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ const createSource = (id: number, updatedAt: string): Source => ({
repoUrl: null,
sourceType: "local",
sourceRef: `/tmp/project-${id}`,
initializationMode: "existing",
gitProvider: "local",
gitHostDomain: null,
defaultBranch: "main",
Expand Down
86 changes: 42 additions & 44 deletions dashboard/src/v2/components/chat/ChatCreateAppQuickActions.tsx
Original file line number Diff line number Diff line change
@@ -1,33 +1,24 @@
import type { FunctionComponent } from "preact";
import { Globe2, Monitor } from "lucide-preact";
import { BriefcaseBusiness, Gamepad2, Globe2, Monitor, ShoppingCart } from "lucide-preact";
import type { DashboardCreateAppQuickactionKind } from "../../types.js";
import { CREATE_APP_QUICKACTION_CATALOG } from "../../../../../src/domain/chat/create-app-quickaction-catalog.js";
import { isInitialOnlyCreateAppQuickaction } from "../../lib/cinematic-quick-actions.js";

const CREATE_APP_ACTIONS: Array<{
kind: DashboardCreateAppQuickactionKind;
label: string;
description: string;
icon: typeof Monitor;
}> = [
{
kind: "desktop_app",
label: "Create Desktop App",
description: "Launch a desktop app sprint",
icon: Monitor,
},
{
kind: "web_app",
label: "Create Web App",
description: "Launch a web app sprint",
icon: Globe2,
},
];
const CREATE_APP_ACTION_ICONS: Record<DashboardCreateAppQuickactionKind, typeof Monitor> = {
web_app: Globe2,
desktop_app: Monitor,
online_shop: ShoppingCart,
portfolio: BriefcaseBusiness,
game: Gamepad2,
};

export const ChatCreateAppQuickActions: FunctionComponent<{
disabled?: boolean;
sending?: boolean;
hasProject: boolean;
showInitialCreateActions: boolean;
onSelect: (kind: DashboardCreateAppQuickactionKind) => void;
}> = ({ disabled = false, sending = false, hasProject, onSelect }) => {
}> = ({ disabled = false, sending = false, hasProject, showInitialCreateActions, onSelect }) => {
const isDisabled = disabled || sending || !hasProject;
const status = !hasProject
? "Create app quick actions are unavailable until a project is selected."
Expand All @@ -37,29 +28,36 @@ export const ChatCreateAppQuickActions: FunctionComponent<{

return (
<div className="min-w-0" aria-label="Create app quick actions">
<div className="flex min-w-0 flex-col gap-2 sm:flex-row">
{CREATE_APP_ACTIONS.map(({ kind, label, description, icon: Icon }) => (
<button
key={kind}
type="button"
onClick={() => onSelect(kind)}
disabled={isDisabled}
aria-disabled={isDisabled}
aria-label={label}
aria-describedby={`create-app-quickaction-${kind}-description create-app-quickaction-status`}
className={`group inline-flex min-h-11 min-w-0 flex-1 items-center justify-center gap-2 rounded-2xl border px-3 py-2 text-[11px] font-bold uppercase tracking-[0.12em] transition-all focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-signal-500/40 ${
isDisabled
? "cursor-not-allowed border-black/[0.06] bg-black/[0.035] text-slate-400 dark:border-white/[0.06] dark:bg-white/[0.04] dark:text-slate-500"
: "border-signal-500/25 bg-signal-500/10 text-signal-700 hover:border-signal-500/45 hover:bg-signal-500/15 hover:text-signal-800 active:scale-[0.98] dark:text-signal-300 dark:hover:text-signal-200"
}`}
>
<Icon className="h-4 w-4 shrink-0" strokeWidth={2.2} aria-hidden="true" />
<span className="min-w-0 truncate">{label}</span>
<span id={`create-app-quickaction-${kind}-description`} className="sr-only">
{description}
</span>
</button>
))}
<div className="flex min-w-0 flex-col gap-2 sm:flex-row sm:flex-wrap">
{CREATE_APP_QUICKACTION_CATALOG.filter(({ kind }) => (
showInitialCreateActions || !isInitialOnlyCreateAppQuickaction(kind)
)).map(({ kind, displayLabel, appKindLabel }) => {
const Icon = CREATE_APP_ACTION_ICONS[kind];
const label = displayLabel;
const description = `Launch ${kind === "online_shop" ? "an" : "a"} ${appKindLabel.toLowerCase()} sprint`;
return (
<button
key={kind}
type="button"
onClick={() => onSelect(kind)}
disabled={isDisabled}
aria-disabled={isDisabled}
aria-label={label}
aria-describedby={`create-app-quickaction-${kind}-description create-app-quickaction-status`}
className={`group inline-flex min-h-11 min-w-0 flex-1 items-center justify-center gap-2 rounded-2xl border px-3 py-2 text-[11px] font-bold uppercase tracking-[0.12em] transition-all focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-signal-500/40 sm:min-w-40 ${
isDisabled
? "cursor-not-allowed border-black/[0.06] bg-black/[0.035] text-slate-400 dark:border-white/[0.06] dark:bg-white/[0.04] dark:text-slate-500"
: "border-signal-500/25 bg-signal-500/10 text-signal-700 hover:border-signal-500/45 hover:bg-signal-500/15 hover:text-signal-800 active:scale-[0.98] dark:text-signal-300 dark:hover:text-signal-200"
}`}
>
<Icon className="h-4 w-4 shrink-0" strokeWidth={2.2} aria-hidden="true" />
<span className="min-w-0 whitespace-normal text-center leading-4">{label}</span>
<span id={`create-app-quickaction-${kind}-description`} className="sr-only">
{description}
</span>
</button>
);
})}
</div>
<div id="create-app-quickaction-status" role="status" aria-live="polite" className="sr-only">
{status}
Expand Down
Loading
Loading