Singularity System Enhancement Plan

Ecosistema completo para organización y gestión de contenido con interfaces espaciales

Singularity System: Comprehensive Enhancement Plan (Updated)

Completed Work (Phases 1-4)

Phase 1: Foundation & Persistence (COMPLETE)

Phase 2: Functional Blocks (COMPLETE)

Phase 3: Database Integration (COMPLETE)

Phase 4: Real-World Demo (COMPLETE)

Recent Critical Fixes (COMPLETE)


Priority Reorganization (Based on User Decisions)

User Decision Summary:

  1. Do Block Configuration + AI features IN PARALLEL (1C)
  2. Export/Import IMMEDIATELY AFTER block config (2A)
  3. Skip multi-user for now - single-user MVP (3B)
  4. AI: Block config assistant + Natural language to flow - BOTH using gograb-ai (4A + 4B)

Phase 5: Block Configuration System (IN PROGRESS - PARALLEL TRACK A)

Goal

Make blocks fully configurable so users can set inputs, operations, and outputs. Everything stored as JSON for shareability.

5.1: Enhanced Block Data Model

File: libs/singularity-lib/src/lib/models/logic-block.interface.ts

Add comprehensive config to LogicBlock interface:

interface LogicBlock {
  id: string;
  name: string;
  type: BlockType;
  category: string;
  
  // NEW: Comprehensive configuration
  config?: {
    // Input configuration
    inputs?: {
      [inputName: string]: {
        type: 'variable' | 'constant' | 'connection';
        value?: any;  // For constants
        variableName?: string;  // For variable references ($a)
        connectionId?: string;  // For port connections
        defaultValue?: any;
      };
    };
    
    // Output configuration
    outputs?: {
      [outputName: string]: {
        variableName?: string;  // Where to store result
      };
    };
    
    // Block-specific settings
    settings?: {
      operation?: string;  // For Calculate: 'add', 'subtract', etc.
      [key: string]: any;
    };
    
    // UI/Visual settings
    ui?: {
      color?: string;
      icon?: string;
      collapsed?: boolean;
    };
  };
  
  // Existing fields
  position?: { x: number; y: number };
  metadata?: any;
}

5.2: Block Configuration Modal Component

New File: libs/singularity-lib/src/lib/components/logic-builder/components/block-config-modal/block-config-modal.component.ts

Create modal component that opens when user double-clicks a block:

5.3: Inline Quick Config

File: libs/singularity-lib/src/lib/components/logic-builder/components/block-card/block-card.component.ts

Add inline editing to block card UI:

5.4: Update Execution Engine to Read Config

File: libs/singularity-lib/src/lib/services/logic-execution-engine.service.ts

Enhance execution to read from block.config:

private async executeBlock(block: LogicBlock, context: ExecutionContext): Promise<any> {
  // NEW: Read from block.config if available
  const args = block.config?.inputs 
    ? this.resolveInputsFromConfig(block.config.inputs, context)
    : block.properties; // Fallback to old properties
    
  // Execute with resolved inputs
  const result = await this.executeBlockType(block, args, context);
  
  // NEW: Store result in configured output variable
  if (block.config?.outputs) {
    Object.entries(block.config.outputs).forEach(([outputName, outputConfig]) => {
      if (outputConfig.variableName) {
        context.variables.set(outputConfig.variableName, result);
      }
    });
  }
  
  return result;
}

Phase 6: AI Integration via gograb-ai (IN PROGRESS - PARALLEL TRACK B)

Goal

Leverage existing gograb-ai infrastructure for block configuration assistant and natural language to flow conversion.

6.1: Block Configuration AI Assistant

New File: libs/singularity-lib/src/lib/components/logic-builder/components/ai-block-assistant/ai-block-assistant.component.ts

Embed lib-simple-ai-chat component for block configuration help:

@Component({
  selector: 'lib-ai-block-assistant',
  template: `
    <div class="ai-block-assistant-panel">
      <h3>AI Block Assistant</h3>
      <p>Describe what you want to do, and I'll configure the block for you!</p>
      
      <!-- Leverage gograb-ai -->
      <lib-simple-ai-chat
        chatId="singularity-block-config"
        title="Block Configuration Assistant"
        [initialProvider]="AIProvider.ANTHROPIC"
        (responseReceived)="onAIBlockConfigResponse($event)"
      ></lib-simple-ai-chat>
    </div>
  `
})
export class AiBlockAssistantComponent {
  private aiFactory = inject(AIFactoryService);
  private singularityService = inject(SingularityService);
  
  onAIBlockConfigResponse(response: string): void {
    // Parse AI response for block configuration
    const config = this.extractBlockConfigFromAI(response);
    if (config) {
      // Apply configuration to selected block
      this.singularityService.updateBlockConfig(this.selectedBlockId, config);
    }
  }
  
  private extractBlockConfigFromAI(response: string): LogicBlockConfig | null {
    // Parse JSON from AI response
    // Look for structured config in response
    const jsonMatch = response.match(/```json\n([\s\S]*?)\n```/);
    if (jsonMatch) {
      return JSON.parse(jsonMatch[1]);
    }
    return null;
  }
}

System Prompt: Configure in component config:

systemPrompt = `You are an AI assistant helping users configure logic blocks in Singularity.
When a user describes what they want, respond with a JSON configuration.

Example: User says "I want to add two numbers a and b"
You respond:
\`\`\`json
{
  "inputs": {
    "a": { "type": "variable", "variableName": "a" },
    "b": { "type": "variable", "variableName": "b" }
  },
  "settings": {
    "operation": "add"
  },
  "outputs": {
    "result": { "variableName": "sum" }
  }
}
\`\`\`

Always respond with JSON in code blocks.`;

6.2: Natural Language to Flow Converter

New File: libs/singularity-lib/src/lib/components/logic-builder/components/nl-to-flow/nl-to-flow.component.ts

Button in Logic Builder header that opens AI chat for flow generation:

@Component({
  selector: 'lib-nl-to-flow',
  template: `
    <div class="nl-to-flow-panel">
      <h3>Describe Your Flow</h3>
      <p>Tell me what you want to build, and I'll create the flow!</p>
      
      <lib-simple-ai-chat
        chatId="singularity-nl-to-flow"
        title="Flow Generation Assistant"
        [initialProvider]="AIProvider.ANTHROPIC"
        (responseReceived)="onAIFlowResponse($event)"
      ></lib-simple-ai-chat>
    </div>
  `
})
export class NlToFlowComponent {
  private aiFactory = inject(AIFactoryService);
  private singularityService = inject(SingularityService);
  private storage = inject(GgStorage);
  
  async onAIFlowResponse(response: string): Promise<void> {
    // Extract flow JSON from AI response
    const flow = this.extractFlowFromAI(response);
    if (flow) {
      // Create blocks and connections
      await this.createFlowFromAI(flow);
    }
  }
  
  private async createFlowFromAI(flowSpec: any): Promise<void> {
    const blocks: LogicBlock[] = [];
    const connections: LogicConnection[] = [];
    
    // Generate blocks from AI spec
    flowSpec.blocks.forEach((blockSpec: any, index: number) => {
      const block: LogicBlock = {
        id: `block_${Date.now()}_${index}`,
        name: blockSpec.name,
        type: blockSpec.type,
        category: blockSpec.category,
        config: blockSpec.config,
        position: { x: 100 + index * 300, y: 200 }
      };
      blocks.push(block);
    });
    
    // Generate connections from AI spec
    flowSpec.connections.forEach((connSpec: any) => {
      const connection: LogicConnection = {
        id: `conn_${Date.now()}_${Math.random()}`,
        sourceBlockId: blocks[connSpec.from].id,
        sourcePortId: 'output',
        targetBlockId: blocks[connSpec.to].id,
        targetPortId: 'input'
      };
      connections.push(connection);
    });
    
    // Set blocks and connections via service
    this.singularityService.setBlocks(blocks);
    this.singularityService.setConnections(connections);
    
    // Save as new flow
    const flow: LogicFlow = {
      id: `flow_${Date.now()}`,
      name: flowSpec.name || 'AI Generated Flow',
      blocks,
      connections,
      metadata: {
        created: new Date(),
        modified: new Date(),
        author: 'AI Assistant',
        description: flowSpec.description || 'Generated by AI'
      }
    };
    
    await this.storage.put(flow.id, flow);
  }
}

System Prompt:

systemPrompt = `You are an AI assistant that generates logic flows for Singularity from natural language.

When a user describes a workflow, respond with a JSON flow specification.

Example: User says "Get user by ID, calculate age, send email if age is 21"
You respond:
\`\`\`json
{
  "name": "Birthday Email Flow",
  "description": "Fetches user, calculates age, sends birthday email if 21",
  "blocks": [
    {
      "name": "Get User",
      "type": "action",
      "category": "database",
      "config": {
        "settings": { "operation": "get", "collection": "users" },
        "inputs": { "userId": { "type": "variable", "variableName": "userId" } },
        "outputs": { "result": { "variableName": "user" } }
      }
    },
    {
      "name": "Calculate Age",
      "type": "function",
      "category": "math",
      "config": {
        "settings": { "operation": "calculate_age" },
        "inputs": { "birthdate": { "type": "variable", "variableName": "user.birthdate" } },
        "outputs": { "result": { "variableName": "age" } }
      }
    },
    {
      "name": "Check Age 21",
      "type": "condition",
      "category": "logic",
      "config": {
        "settings": { "condition": "$age === 21" }
      }
    },
    {
      "name": "Send Birthday Email",
      "type": "action",
      "category": "communication",
      "config": {
        "settings": { "operation": "send_email" },
        "inputs": { 
          "to": { "type": "variable", "variableName": "user.email" },
          "subject": { "type": "constant", "value": "Happy Birthday!" }
        }
      }
    }
  ],
  "connections": [
    { "from": 0, "to": 1 },
    { "from": 1, "to": 2 },
    { "from": 2, "to": 3 }
  ]
}
\`\`\`

Always respond with JSON in code blocks.`;

6.3: AI Panel in Logic Builder

File: libs/singularity-lib/src/lib/components/logic-builder/logic-builder.component.html

Add AI panel toggle button in header:

<div class="logic-builder-header">
  <!-- Existing buttons -->
  <button (click)="toggleAIPanel()" title="AI Assistant">
    <i class="fas fa-robot"></i> AI
  </button>
</div>

<!-- AI Panel (slides in from right) -->
<div class="ai-panel" *ngIf="showAIPanel()">
  <ux-tabs>
    <ux-tab label="Block Config">
      <lib-ai-block-assistant></lib-ai-block-assistant>
    </ux-tab>
    <ux-tab label="Generate Flow">
      <lib-nl-to-flow></lib-nl-to-flow>
    </ux-tab>
  </ux-tabs>
</div>

Phase 7: Export/Import System (AFTER Phase 5 & 6)

Goal

Complete JSON export/import so configured flows can be shared.

7.1: Export Flow Interface

File: libs/singularity-lib/src/lib/models/exported-flow.interface.ts

interface ExportedFlow {
  version: '1.0.0';
  flowId: string;
  flowName: string;
  description: string;
  author: string;
  created: string;
  modified: string;
  
  // Complete flow data (INCLUDING block.config!)
  blocks: LogicBlock[];  // Now with full config
  connections: LogicConnection[];
  
  // Metadata
  requiredVariables: string[];  // Variables this flow expects
  outputVariables: string[];    // Variables this flow produces
  dependencies: string[];       // External dependencies
  
  // Visual state
  canvasState: {
    zoom: number;
    panX: number;
    panY: number;
  };
}

7.2: Export Service

File: libs/singularity-lib/src/lib/services/flow-export.service.ts

@Injectable({ providedIn: 'root' })
export class FlowExportService {
  async exportFlow(flowId: string): Promise<ExportedFlow> {
    const flow = await this.storage.get<LogicFlow>(flowId);
    
    return {
      version: '1.0.0',
      flowId: flow.id,
      flowName: flow.name,
      description: flow.metadata?.description || '',
      author: flow.metadata?.author || 'Unknown',
      created: flow.metadata?.created?.toISOString() || '',
      modified: flow.metadata?.modified?.toISOString() || '',
      blocks: flow.blocks,  // Includes block.config
      connections: flow.connections,
      requiredVariables: this.extractRequiredVariables(flow.blocks),
      outputVariables: this.extractOutputVariables(flow.blocks),
      dependencies: [],
      canvasState: this.getCanvasState()
    };
  }
  
  downloadAsJSON(exportedFlow: ExportedFlow): void {
    const json = JSON.stringify(exportedFlow, null, 2);
    const blob = new Blob([json], { type: 'application/json' });
    const url = URL.createObjectURL(blob);
    const a = document.createElement('a');
    a.href = url;
    a.download = `${exportedFlow.flowName}.json`;
    a.click();
    URL.revokeObjectURL(url);
  }
  
  copyToClipboard(exportedFlow: ExportedFlow): void {
    const json = JSON.stringify(exportedFlow);
    const encoded = btoa(json);
    const shareUrl = `https://gograb.space/singularity/import?flow=${encoded}`;
    navigator.clipboard.writeText(shareUrl);
  }
}

7.3: Import Service

File: libs/singularity-lib/src/lib/services/flow-import.service.ts

@Injectable({ providedIn: 'root' })
export class FlowImportService {
  async importFromFile(file: File): Promise<void> {
    const text = await file.text();
    const exportedFlow: ExportedFlow = JSON.parse(text);
    await this.importFlow(exportedFlow);
  }
  
  async importFromJSON(json: string): Promise<void> {
    const exportedFlow: ExportedFlow = JSON.parse(json);
    await this.importFlow(exportedFlow);
  }
  
  async importFromURL(encodedFlow: string): Promise<void> {
    const json = atob(encodedFlow);
    const exportedFlow: ExportedFlow = JSON.parse(json);
    await this.importFlow(exportedFlow);
  }
  
  private async importFlow(exportedFlow: ExportedFlow, mode: 'replace' | 'merge' | 'new' = 'new'): Promise<void> {
    // Validate version
    if (exportedFlow.version !== '1.0.0') {
      throw new Error('Unsupported flow version');
    }
    
    // Create new flow or update existing
    const flow: LogicFlow = {
      id: mode === 'new' ? `flow_${Date.now()}` : exportedFlow.flowId,
      name: exportedFlow.flowName,
      blocks: exportedFlow.blocks,  // Includes block.config
      connections: exportedFlow.connections,
      metadata: {
        created: new Date(exportedFlow.created),
        modified: new Date(),
        author: exportedFlow.author,
        description: exportedFlow.description
      }
    };
    
    // Save to storage
    await this.storage.put(flow.id, flow);
    
    // Load in Logic Builder
    await this.loadFlowInBuilder(flow.id);
  }
}

7.4: UI Buttons

File: libs/singularity-lib/src/lib/components/logic-builder/logic-builder.component.html

Add export/import buttons:

<div class="logic-builder-header">
  <!-- Existing buttons -->
  
  <!-- Export/Import -->
  <button (click)="exportFlow()" title="Export Flow">
    <i class="fas fa-download"></i> Export
  </button>
  <button (click)="importFlow()" title="Import Flow">
    <i class="fas fa-upload"></i> Import
  </button>
</div>

Phase 8: Enhanced UX (AFTER Phase 7)

8.1: Block Templates Library

8.2: Smart Variable Suggestions

8.3: Block Search & Filtering

8.4: Visual Enhancements


Phase 9: Testing & Validation (AFTER Phase 8)

9.1: Unit Tests

9.2: Integration Tests

9.3: Flow Validation


Implementation Order

Sprint 5 (Current): Parallel Tracks

Track A: Block Configuration (Phase 5)

  1. Enhanced block data model
  2. Block configuration modal component
  3. Update execution engine to read config
  4. Inline quick config

Track B: AI Integration (Phase 6)

  1. AI block assistant component (gograb-ai integration)
  2. Natural language to flow component
  3. AI panel in Logic Builder
  4. System prompts and response parsing

Sprint 6: Export/Import (Phase 7)

  1. Export flow interface and service
  2. Import flow service
  3. UI buttons and file handling
  4. Share URL generation

Sprint 7: Enhanced UX (Phase 8)

  1. Block templates library
  2. Smart variable suggestions
  3. Block search and filtering
  4. Visual enhancements

Sprint 8: Testing & Polish (Phase 9)

  1. Unit tests
  2. Integration tests
  3. Flow validation
  4. Documentation

Success Metrics

Technical

User Experience

Functionality


Key Files Summary

New Files (Phase 5-7)

  1. libs/singularity-lib/src/lib/components/logic-builder/components/block-config-modal/ (component, template, styles)
  2. libs/singularity-lib/src/lib/components/logic-builder/components/ai-block-assistant/ (component)
  3. libs/singularity-lib/src/lib/components/logic-builder/components/nl-to-flow/ (component)
  4. libs/singularity-lib/src/lib/models/exported-flow.interface.ts
  5. libs/singularity-lib/src/lib/services/flow-export.service.ts
  6. libs/singularity-lib/src/lib/services/flow-import.service.ts

Modified Files (Phase 5-7)

  1. libs/singularity-lib/src/lib/models/logic-block.interface.ts (add config)
  2. libs/singularity-lib/src/lib/services/logic-execution-engine.service.ts (read config)
  3. libs/singularity-lib/src/lib/services/singularity.service.ts (updateBlockConfig method)
  4. libs/singularity-lib/src/lib/components/logic-builder/logic-builder.component.html (AI panel, export/import buttons)
  5. libs/singularity-lib/src/lib/components/logic-builder/logic-builder.component.ts (toggleAIPanel, exportFlow, importFlow methods)
  6. libs/singularity-lib/src/lib/components/logic-builder/components/block-card/block-card.component.ts (inline quick config)

Notes