Add initial project structure with essential files
- Created .gitignore to exclude build artifacts and dependencies. - Added index.html as the main entry point for the application. - Included LICENSE file with Apache 2.0 terms. - Initialized package.json and package-lock.json for project dependencies. - Added pnpm-lock.yaml for package management. - Created QUICKSTART.md for setup instructions. - Added README.md and README.zh-CN.md for project documentation in English and Chinese.
This commit is contained in:
+210
@@ -0,0 +1,210 @@
|
||||
export type ExecMode = 'daemon' | 'api';
|
||||
|
||||
export interface AppConfig {
|
||||
mode: ExecMode;
|
||||
apiKey: string;
|
||||
baseUrl: string;
|
||||
model: string;
|
||||
agentId: string | null;
|
||||
skillId: string | null;
|
||||
designSystemId: string | null;
|
||||
// True once the user has been through the welcome onboarding modal at
|
||||
// least once (saved or skipped). Bootstrap skips the auto-popup when
|
||||
// this is set so refreshing the page doesn't re-prompt.
|
||||
onboardingCompleted?: boolean;
|
||||
}
|
||||
|
||||
export type AgentEvent =
|
||||
| { kind: 'status'; label: string; detail?: string | undefined }
|
||||
| { kind: 'text'; text: string }
|
||||
| { kind: 'thinking'; text: string }
|
||||
| { kind: 'tool_use'; id: string; name: string; input: unknown }
|
||||
| { kind: 'tool_result'; toolUseId: string; content: string; isError: boolean }
|
||||
| { kind: 'usage'; inputTokens?: number; outputTokens?: number; costUsd?: number; durationMs?: number }
|
||||
| { kind: 'raw'; line: string };
|
||||
|
||||
export interface ChatMessage {
|
||||
id: string;
|
||||
role: 'user' | 'assistant';
|
||||
content: string;
|
||||
events?: AgentEvent[];
|
||||
startedAt?: number;
|
||||
endedAt?: number;
|
||||
// Files staged by the user on this turn (uploaded into the project
|
||||
// folder). Persisted on the message so re-renders show the same chips.
|
||||
attachments?: ChatAttachment[];
|
||||
// Files that appeared in the project folder during this assistant turn.
|
||||
// Rendered as download / open chips at the end of the message so the
|
||||
// user can grab a generated artifact (.pptx, .zip, etc.) in one click.
|
||||
producedFiles?: ProjectFile[];
|
||||
}
|
||||
|
||||
// Reference to a file that lives in the active project folder. The user
|
||||
// stages these by paste / drop / picker / @-mention; the daemon receives
|
||||
// `path` on the chat call and the agent reads them from cwd.
|
||||
export interface ChatAttachment {
|
||||
path: string;
|
||||
name: string;
|
||||
kind: 'image' | 'file';
|
||||
size?: number;
|
||||
}
|
||||
|
||||
export interface Artifact {
|
||||
identifier: string;
|
||||
title: string;
|
||||
html: string;
|
||||
savedUrl?: string;
|
||||
}
|
||||
|
||||
export interface ExamplePreview {
|
||||
source: 'skill' | 'design-system';
|
||||
id: string;
|
||||
title: string;
|
||||
html: string;
|
||||
}
|
||||
|
||||
export interface AgentInfo {
|
||||
id: string;
|
||||
name: string;
|
||||
bin: string;
|
||||
available: boolean;
|
||||
path?: string;
|
||||
version?: string | null;
|
||||
}
|
||||
|
||||
export interface SkillSummary {
|
||||
id: string;
|
||||
name: string;
|
||||
description: string;
|
||||
triggers: string[];
|
||||
mode: 'prototype' | 'deck' | 'template' | 'design-system';
|
||||
platform?: 'desktop' | 'mobile' | null;
|
||||
scenario?: string | null;
|
||||
previewType: string;
|
||||
designSystemRequired: boolean;
|
||||
defaultFor: string[];
|
||||
upstream: string | null;
|
||||
/** Lower number = higher priority in the Examples gallery. `null` keeps
|
||||
* the skill in its natural alphabetical position below all featured
|
||||
* entries. Set via `ocd.featured` in the SKILL.md frontmatter. */
|
||||
featured?: number | null;
|
||||
hasBody: boolean;
|
||||
examplePrompt: string;
|
||||
}
|
||||
|
||||
export interface SkillDetail extends SkillSummary {
|
||||
body: string;
|
||||
}
|
||||
|
||||
export interface DesignSystemSummary {
|
||||
id: string;
|
||||
title: string;
|
||||
category: string;
|
||||
summary: string;
|
||||
/** 4 representative hex strings extracted from DESIGN.md: [bg, support, fg, accent].
|
||||
* Empty when DESIGN.md doesn't expose its tokens in the bold-and-hex format. */
|
||||
swatches?: string[];
|
||||
}
|
||||
|
||||
export interface DesignSystemDetail extends DesignSystemSummary {
|
||||
body: string;
|
||||
}
|
||||
|
||||
export type ProjectFileKind =
|
||||
| 'html'
|
||||
| 'image'
|
||||
| 'sketch'
|
||||
| 'text'
|
||||
| 'code'
|
||||
| 'binary';
|
||||
|
||||
export interface ProjectFile {
|
||||
name: string;
|
||||
// Project-relative path. Today the project folder is flat so `path`
|
||||
// equals `name` for every file — but components that want to think in
|
||||
// path terms (the @-mention picker, the staged-attachment chips) can
|
||||
// read this without caring whether subdirs exist.
|
||||
path?: string;
|
||||
// Discriminator for code that wants to filter files vs dirs in a tree
|
||||
// listing. The current listing is files-only; we always set this to
|
||||
// 'file' so the discriminator is meaningful.
|
||||
type?: 'file' | 'dir';
|
||||
size: number;
|
||||
mtime: number;
|
||||
kind: ProjectFileKind;
|
||||
mime: string;
|
||||
}
|
||||
|
||||
// Per-project metadata captured at creation time. The agent reads this
|
||||
// during chat (via the system prompt) and the question-form re-asks for
|
||||
// any field that's missing. Each `kind` carries a different shape.
|
||||
export type ProjectKind = 'prototype' | 'deck' | 'template' | 'other';
|
||||
|
||||
export interface ProjectMetadata {
|
||||
kind: ProjectKind;
|
||||
// Prototype: 'wireframe' | 'high-fidelity'. Drives the visual ambition.
|
||||
fidelity?: 'wireframe' | 'high-fidelity';
|
||||
// Slide deck: whether the user wants speaker notes (less text per slide).
|
||||
speakerNotes?: boolean;
|
||||
// Template: whether motion/animation should be part of the design.
|
||||
// Defaults `false` so a static template stays static unless asked.
|
||||
animations?: boolean;
|
||||
// Template: id of the user-saved template chosen at creation time.
|
||||
// Only set on `kind === 'template'` projects (the other kinds dropped
|
||||
// template selection entirely). The built-in 'animation' starter no
|
||||
// longer ships — every template here is user-created via Share menu.
|
||||
templateId?: string;
|
||||
// Template: human-readable label of the source template, kept separate
|
||||
// from `templateId` so the agent surface can name it without re-fetching.
|
||||
templateLabel?: string;
|
||||
// Multi-select design-system "inspirations". The first pick still goes to
|
||||
// `Project.designSystemId` (the primary system that controls tokens); any
|
||||
// additional ids land here and are passed to the agent as references the
|
||||
// generated artifact should *also* draw from. Empty / undefined when the
|
||||
// user stayed in single-select mode.
|
||||
inspirationDesignSystemIds?: string[];
|
||||
}
|
||||
|
||||
export interface Project {
|
||||
id: string;
|
||||
name: string;
|
||||
skillId: string | null;
|
||||
designSystemId: string | null;
|
||||
createdAt: number;
|
||||
updatedAt: number;
|
||||
// The prompt that should be prefilled into the chat composer when the
|
||||
// project is opened. Cleared the first time the project is opened so it
|
||||
// doesn't keep re-populating on subsequent visits.
|
||||
pendingPrompt?: string;
|
||||
// Optional structured metadata captured by the new-project panel. The
|
||||
// shape varies by `kind`. Older projects created before this field
|
||||
// existed will have it `undefined`.
|
||||
metadata?: ProjectMetadata;
|
||||
}
|
||||
|
||||
export interface ProjectTemplate {
|
||||
id: string;
|
||||
name: string;
|
||||
// Source project the template was captured from (so we can show "based
|
||||
// on …" in the picker). Optional because some templates are seeded.
|
||||
sourceProjectId?: string;
|
||||
// Snapshot of HTML files at the moment the template was saved. Each
|
||||
// entry is a basename → text content pair.
|
||||
files: Array<{ name: string; content: string }>;
|
||||
// Free-form description shown in the picker.
|
||||
description?: string;
|
||||
createdAt: number;
|
||||
}
|
||||
|
||||
export interface Conversation {
|
||||
id: string;
|
||||
projectId: string;
|
||||
title: string | null;
|
||||
createdAt: number;
|
||||
updatedAt: number;
|
||||
}
|
||||
|
||||
export interface OpenTabsState {
|
||||
tabs: string[];
|
||||
active: string | null;
|
||||
}
|
||||
Reference in New Issue
Block a user