Adding the skills
This commit is contained in:
Generated
+10
@@ -0,0 +1,10 @@
|
||||
{
|
||||
"name": "@glitch-university/glitch-components-workspace",
|
||||
"lockfileVersion": 3,
|
||||
"requires": true,
|
||||
"packages": {
|
||||
"": {
|
||||
"name": "@glitch-university/glitch-components-workspace"
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -27,14 +27,14 @@ function parseArgs(argv) {
|
||||
const options = {
|
||||
command,
|
||||
components: [],
|
||||
hostDir: '',
|
||||
hostDirs: [],
|
||||
stagingDir: path.join(cwd, '.glitch-release')
|
||||
}
|
||||
|
||||
for (let index = 0; index < rest.length; index += 1) {
|
||||
const arg = rest[index]
|
||||
if (arg === '--host') {
|
||||
options.hostDir = path.resolve(cwd, rest[index + 1] ?? '')
|
||||
options.hostDirs.push(path.resolve(cwd, rest[index + 1] ?? ''))
|
||||
index += 1
|
||||
continue
|
||||
}
|
||||
@@ -176,6 +176,14 @@ function ensureDirectory(directory) {
|
||||
fs.mkdirSync(directory, { recursive: true })
|
||||
}
|
||||
|
||||
function getDefaultHostDirs() {
|
||||
return [
|
||||
path.resolve(cwd, '..', 'gnommoweb', 'public', 'glitch'),
|
||||
path.resolve(cwd, '..', 'gnommoplayer', 'public', 'glitch'),
|
||||
path.resolve(cwd, '..', 'gnommoeditor', 'public', 'glitch')
|
||||
]
|
||||
}
|
||||
|
||||
function copyDirectoryContents(sourceDir, destinationDir) {
|
||||
ensureDirectory(destinationDir)
|
||||
for (const entry of fs.readdirSync(sourceDir)) {
|
||||
@@ -186,7 +194,7 @@ function copyDirectoryContents(sourceDir, destinationDir) {
|
||||
}
|
||||
}
|
||||
|
||||
function releaseComponent(component, hostDir, stagingDir) {
|
||||
function releaseComponent(component, hostDirs, stagingDir) {
|
||||
const distDir = path.join(component.componentDir, 'dist')
|
||||
if (!fs.existsSync(distDir)) {
|
||||
fail(`Missing dist directory for ${component.componentDirName}. Run build first.`)
|
||||
@@ -205,9 +213,11 @@ function releaseComponent(component, hostDir, stagingDir) {
|
||||
tags: ['legacy']
|
||||
}
|
||||
|
||||
for (const hostDir of hostDirs) {
|
||||
const releaseDir = path.join(hostDir, manifest.folderName)
|
||||
copyDirectoryContents(distDir, releaseDir)
|
||||
fs.writeFileSync(path.join(releaseDir, 'glitch.manifest.json'), `${JSON.stringify(manifest, null, 2)}\n`)
|
||||
}
|
||||
|
||||
const stagingComponentDir = path.join(stagingDir, manifest.folderName)
|
||||
copyDirectoryContents(distDir, stagingComponentDir)
|
||||
@@ -268,17 +278,17 @@ switch (options.command) {
|
||||
}
|
||||
|
||||
case 'release': {
|
||||
const hostDir =
|
||||
options.hostDir ||
|
||||
path.resolve(cwd, '..', 'gnommoweb', 'src', 'components', 'glitch')
|
||||
const hostDirs = options.hostDirs.length > 0 ? options.hostDirs : getDefaultHostDirs()
|
||||
|
||||
for (const hostDir of hostDirs) {
|
||||
ensureDirectory(hostDir)
|
||||
}
|
||||
ensureDirectory(options.stagingDir)
|
||||
|
||||
for (const component of components) {
|
||||
console.log(`=== Releasing ${component.componentDirName} ===`)
|
||||
runBuild(component)
|
||||
releaseComponent(component, hostDir, options.stagingDir)
|
||||
releaseComponent(component, hostDirs, options.stagingDir)
|
||||
}
|
||||
break
|
||||
}
|
||||
|
||||
+12
-31
@@ -1,12 +1,4 @@
|
||||
#!/bin/bash
|
||||
# Sets up git remotes for all glitch-component folders and pushes to ramanujan.
|
||||
#
|
||||
# Usage:
|
||||
# ./setup-remotes.sh # set remotes only
|
||||
# ./setup-remotes.sh --push # set remotes and push all
|
||||
#
|
||||
# Reads GIT_USER / GIT_PASSWORD from ../.env if present, otherwise prompts.
|
||||
|
||||
set -e
|
||||
|
||||
REMOTE_HOST="ramanujan.glitch.university"
|
||||
@@ -14,34 +6,17 @@ COMPONENTS_DIR="$(cd "$(dirname "$0")" && pwd)"
|
||||
PUSH=false
|
||||
[[ "$1" == "--push" ]] && PUSH=true
|
||||
|
||||
# ── Load credentials ──────────────────────────────────────────────────────────
|
||||
REMOTE_BASE="ssh://git@${REMOTE_HOST}/git/repos"
|
||||
|
||||
ENV_FILE="$COMPONENTS_DIR/../gnommoweb/.env.prod"
|
||||
if [ -f "$ENV_FILE" ]; then
|
||||
GIT_USER=$(grep -E '^GIT_USER=' "$ENV_FILE" | cut -d= -f2 | tr -d '"'"'" | head -1)
|
||||
GIT_PASSWORD=$(grep -E '^GIT_PASSWORD=' "$ENV_FILE" | cut -d= -f2 | tr -d '"'"'" | head -1)
|
||||
fi
|
||||
|
||||
if [ -z "$GIT_USER" ] || [ -z "$GIT_PASSWORD" ]; then
|
||||
read -rp "Git username: " GIT_USER
|
||||
read -rsp "Git password: " GIT_PASSWORD
|
||||
echo
|
||||
fi
|
||||
|
||||
REMOTE_BASE="https://${GIT_USER}:${GIT_PASSWORD}@${REMOTE_HOST}"
|
||||
|
||||
# ── Process each component folder ─────────────────────────────────────────────
|
||||
|
||||
for dir in "$COMPONENTS_DIR"/*/; do
|
||||
name=$(basename "$dir")
|
||||
|
||||
# Skip the skills folder and any non-component entries
|
||||
[[ "$name" == "skills" ]] && continue
|
||||
|
||||
echo "── $name"
|
||||
cd "$dir"
|
||||
|
||||
# Init if not already a git repo
|
||||
if [ ! -d ".git" ]; then
|
||||
git init -q
|
||||
git add -A
|
||||
@@ -49,21 +24,27 @@ for dir in "$COMPONENTS_DIR"/*/; do
|
||||
echo " initialised"
|
||||
fi
|
||||
|
||||
# Add or update remote
|
||||
REMOTE_URL="https://${REMOTE_HOST}/${name}.git"
|
||||
|
||||
if git remote get-url origin &>/dev/null; then
|
||||
git remote set-url origin "${REMOTE_BASE}/${name}.git"
|
||||
git remote set-url origin "$REMOTE_URL"
|
||||
echo " remote updated"
|
||||
else
|
||||
git remote add origin "${REMOTE_BASE}/${name}.git"
|
||||
git remote add origin "$REMOTE_URL"
|
||||
echo " remote added"
|
||||
fi
|
||||
|
||||
# Push
|
||||
if $PUSH; then
|
||||
if ssh git@"$REMOTE_HOST" create-repo "${name}.git" 2>/dev/null; then
|
||||
echo " remote repo ensured"
|
||||
else
|
||||
echo " remote repo may already exist"
|
||||
fi
|
||||
|
||||
if git push -u origin main -q 2>/dev/null || git push -u origin master:main -q 2>/dev/null; then
|
||||
echo " pushed"
|
||||
else
|
||||
echo " push failed (repo may not exist on server yet)"
|
||||
echo " push failed"
|
||||
fi
|
||||
fi
|
||||
|
||||
|
||||
@@ -0,0 +1,92 @@
|
||||
# GlitchComponent Contract (Canonical Shape)
|
||||
|
||||
Use the local `lightlane` project as the canonical source when available:
|
||||
|
||||
- `../lightlane/src/types.ts`
|
||||
- `../lightlane/src/index.tsx`
|
||||
|
||||
This reference captures the current shape observed in `lightlane` so the skill can scaffold quickly.
|
||||
|
||||
## Required Exports
|
||||
|
||||
`src/index.tsx` should export:
|
||||
|
||||
- `default` component
|
||||
- `metadata` object (`GlitchComponentMetadata`)
|
||||
- relevant types re-exported from `src/types.ts`
|
||||
|
||||
## Core Types (Current Lightlane-Compatible Shape)
|
||||
|
||||
```ts
|
||||
export interface GlitchComponentConfig {
|
||||
id: string;
|
||||
name: string;
|
||||
version: string;
|
||||
params: Record<string, unknown>;
|
||||
}
|
||||
|
||||
export interface GlitchTheme {
|
||||
primary: string;
|
||||
accent: string;
|
||||
bg: string;
|
||||
bgSecondary: string;
|
||||
text: string;
|
||||
textMuted: string;
|
||||
border: string;
|
||||
}
|
||||
|
||||
export interface GlitchComponentResult {
|
||||
success: boolean;
|
||||
score?: number;
|
||||
data?: unknown;
|
||||
error?: string;
|
||||
}
|
||||
|
||||
export interface GlitchComponentProps {
|
||||
config: GlitchComponentConfig;
|
||||
onComplete: (result: GlitchComponentResult) => void;
|
||||
onProgress?: (percent: number) => void;
|
||||
theme?: GlitchTheme;
|
||||
className?: string;
|
||||
}
|
||||
|
||||
export interface ParamSchema {
|
||||
[key: string]: {
|
||||
type: 'number' | 'string' | 'boolean' | 'color' | 'select' | 'range';
|
||||
label?: string;
|
||||
description?: string;
|
||||
default: unknown;
|
||||
options?: { value: string | number; label: string }[];
|
||||
min?: number;
|
||||
max?: number;
|
||||
step?: number;
|
||||
};
|
||||
}
|
||||
|
||||
export interface GlitchComponentMetadata {
|
||||
name: string;
|
||||
displayName: string;
|
||||
version: string;
|
||||
paramSchema: ParamSchema;
|
||||
defaultParams: Record<string, unknown>;
|
||||
}
|
||||
```
|
||||
|
||||
## Metadata Expectations
|
||||
|
||||
- `name`: kebab-case slug used by host registration
|
||||
- `displayName`: human-friendly title
|
||||
- `version`: semantic version string
|
||||
- `paramSchema`: controls/settings schema for host and dev harness
|
||||
- `defaultParams`: values that produce a working component without additional configuration
|
||||
|
||||
## Behavioral Expectations
|
||||
|
||||
- Call `onComplete(...)` when the experience completes or fails definitively.
|
||||
- Call `onProgress(percent)` for multi-step flows when progress is meaningful.
|
||||
- Use `config.params` as the single source of runtime config.
|
||||
- Respect `theme` if provided, but keep fallbacks for standalone mode.
|
||||
|
||||
## Validation Tip
|
||||
|
||||
Before finalizing a scaffold, compare generated `src/types.ts` and `src/index.tsx` against the current `../lightlane/src/types.ts` and `../lightlane/src/index.tsx` to catch drift.
|
||||
@@ -0,0 +1,14 @@
|
||||
# Create GlitchComponent
|
||||
|
||||
The canonical Glitch University component workflow now lives at the workspace root:
|
||||
|
||||
- `/Users/jenstandstad/Projects/glitch-components/GLITCH_COMPONENT_STANDARD.md`
|
||||
- `/Users/jenstandstad/Projects/glitch-components/templates/react-vite-glitch-component/`
|
||||
- `/Users/jenstandstad/Projects/glitch-components/scripts/new-glitch-component.mjs`
|
||||
|
||||
Use the root scaffold instead of copying this folder or reusing older component boilerplate.
|
||||
|
||||
For special features suchas 3D, Sound bridge etc consider the referenes in
|
||||
|
||||
/Users/jenstandstad/Projects/glitch-components/skills/references
|
||||
|
||||
@@ -0,0 +1,34 @@
|
||||
# Sound Bridge Notes
|
||||
|
||||
Glitch University uses a host-managed sound system (Howler-based) with string sound keys, for example:
|
||||
|
||||
- `playSound('ui.button_click')`
|
||||
- `playSound('ui.button_hover')`
|
||||
|
||||
## Recommendation
|
||||
|
||||
Treat sound as an optional host integration:
|
||||
|
||||
- Use a small wrapper function in the component (`safePlaySound`) that checks whether a host sound function exists.
|
||||
- No-op when unavailable (standalone dev should still run).
|
||||
- Keep sound identifiers as strings/constants so they match host definitions.
|
||||
|
||||
## Example Pattern
|
||||
|
||||
```ts
|
||||
type PlaySound = (id: string) => void;
|
||||
|
||||
export function safePlaySound(playSound: PlaySound | undefined, id: string) {
|
||||
try {
|
||||
playSound?.(id);
|
||||
} catch {
|
||||
// Ignore host sound errors in standalone/local mode
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Unknowns to Confirm Later
|
||||
|
||||
- How the host exposes `playSound` to glitch-components (prop, context, global import, event bus)
|
||||
- Which sound keys are safe/standardized across experiences
|
||||
- Whether completion/reward sounds are triggered by host or component
|
||||
Reference in New Issue
Block a user