Files
microdao-daarion/docs/tasks/TASK_PHASE_MICRODAO_ROOMS_INTEGRATION_v1.md
Apple a7adddb60d feat: MicroDAO Rooms Integration
Backend:
- GET /city/microdao/{slug}/agents - list agents with roles
- Seed: 6 rooms for DAARION, 3+ rooms for each District

Task doc: TASK_PHASE_MICRODAO_ROOMS_INTEGRATION_v1.md
2025-11-30 11:48:44 -08:00

10 KiB
Raw Blame History

TASK_PHASE_MICRODAO_ROOMS_INTEGRATION_v1

Version: 1.0 Status: Ready Priority: High (City → District → MicroDAO контур)


1. МЕТА

Повністю інтегрувати Rooms Layer для MicroDAO:

  • кожен MicroDAO має стандартний набір кімнат
  • кімнати прив'язані до Matrix
  • UI відображає кімнати з можливістю переходу та чату

2. ВИХІДНІ ДАНІ

Вже є:

  • City Rooms (/city/{slug}) — 100%
  • District Portals (/districts/{slug}) — 100%
  • Matrix Integration — 100%
  • Chat Widget — 100%
  • Базова сторінка /microdao/{slug}

Потрібно:

  • API для кімнат MicroDAO
  • Стандартні room-types
  • UI секція кімнат на сторінці MicroDAO
  • Seed data для існуючих MicroDAO

3. SCOPE

  1. Backend API:

    • GET /api/v1/microdao/{slug}/rooms
    • GET /api/v1/microdao/{slug}/agents
    • POST /api/v1/microdao/{slug}/rooms
  2. Стандартні room-types для MicroDAO

  3. Frontend:

    • Секція "Кімнати MicroDAO"
    • Секція "Агенти MicroDAO"
    • Chat Widget для lobby
  4. Seed Data для DAARION та Districts

  5. Matrix auto-create для нових кімнат


4. МОДУЛЬ 1 — BACKEND API

4.1. GET /api/v1/microdao/{slug}/rooms

Повертає список кімнат MicroDAO.

[
  {
    "id": "room_microdao_daarion-lobby",
    "slug": "daarion-lobby",
    "name": "DAARION Lobby",
    "description": "Головна кімната DAARION DAO",
    "room_role": "lobby",
    "is_public": true,
    "matrix_room_id": "!abc:daarion.space",
    "matrix_room_alias": "#daarion-lobby:daarion.space"
  },
  ...
]

4.2. GET /api/v1/microdao/{slug}/agents

Повертає агентів MicroDAO.

[
  {
    "id": "daarwizz",
    "name": "DAARWIZZ",
    "kind": "governance",
    "role": "orchestrator",
    "is_core": true,
    "status": "active"
  },
  ...
]

4.3. POST /api/v1/microdao/{slug}/rooms

Створює нову кімнату для MicroDAO.

Request:

{
  "slug": "daarion-treasury",
  "name": "Treasury",
  "description": "Фінанси та токеноміка",
  "room_role": "treasury",
  "is_public": false
}

Response: створена кімната з matrix_room_id


5. МОДУЛЬ 2 — СТАНДАРТНІ ROOM-TYPES

Кожен MicroDAO має мати набір кімнат:

room_role Назва Опис is_public
lobby {DAO} Lobby Головна кімната true
governance Governance Голосування, пропозиції true
operations Operations Операційна діяльність false
knowledge Knowledge Base Документація, FAQ true
treasury Treasury Фінанси, токеноміка false
ai-core AI Core Агенти, автоматизація false

6. МОДУЛЬ 3 — REPO_CITY МЕТОДИ

async def get_microdao_rooms(microdao_id: str) -> List[Dict]:
    """Отримати кімнати MicroDAO"""
    query = """
        SELECT id, slug, name, description, room_role, is_public,
               matrix_room_id, matrix_room_alias
        FROM city_rooms
        WHERE owner_id = $1 AND owner_type = 'microdao'
        ORDER BY sort_order, name
    """
    rows = await pool.fetch(query, microdao_id)
    return [dict(r) for r in rows]

async def get_microdao_agents(microdao_id: str) -> List[Dict]:
    """Отримати агентів MicroDAO"""
    query = """
        SELECT a.id, a.display_name as name, a.kind, a.status,
               a.avatar_url, ma.role, ma.is_core
        FROM agents a
        JOIN microdao_agents ma ON ma.agent_id = a.id
        WHERE ma.microdao_id = $1
        ORDER BY ma.is_core DESC, a.display_name
    """
    rows = await pool.fetch(query, microdao_id)
    return [dict(r) for r in rows]

async def create_microdao_room(
    microdao_id: str,
    slug: str,
    name: str,
    description: str,
    room_role: str,
    is_public: bool = True
) -> Dict:
    """Створити кімнату для MicroDAO з Matrix"""
    # 1. Create Matrix room
    matrix_room_id, matrix_room_alias = await ensure_room_has_matrix(
        slug, name, "public" if is_public else "private"
    )
    
    # 2. Insert into DB
    room_id = f"room_microdao_{slug}"
    query = """
        INSERT INTO city_rooms (
            id, slug, name, description, created_by,
            owner_type, owner_id, room_role, is_public,
            matrix_room_id, matrix_room_alias, sort_order
        )
        VALUES ($1, $2, $3, $4, 'u_system', 'microdao', $5, $6, $7, $8, $9, $10)
        RETURNING *
    """
    sort_order = {
        'lobby': 10, 'governance': 20, 'operations': 30,
        'knowledge': 40, 'treasury': 50, 'ai-core': 60
    }.get(room_role, 100)
    
    row = await pool.fetchrow(
        query, room_id, slug, name, description,
        microdao_id, room_role, is_public,
        matrix_room_id, matrix_room_alias, sort_order
    )
    return dict(row)

7. МОДУЛЬ 4 — FRONTEND

7.1. Оновити /microdao/[slug]/page.tsx

Додати секції:

  • MicroDAO Rooms (список кімнат з картками)
  • MicroDAO Agents (список агентів)
  • Chat Widget для lobby room

7.2. Компонент MicroDAORoomsSection

function MicroDAORoomsSection({ rooms }: { rooms: Room[] }) {
  return (
    <div className="glass-panel p-6">
      <h3 className="text-lg font-semibold text-white mb-4">
        <Building2 /> Кімнати MicroDAO
      </h3>
      <div className="grid grid-cols-2 gap-3">
        {rooms.map(room => (
          <Link href={`/city/${room.slug}`} key={room.id}>
            <div className="p-4 bg-white/5 rounded-xl hover:bg-white/10">
              <p className="font-medium text-white">{room.name}</p>
              <p className="text-xs text-slate-400">{room.room_role}</p>
              {room.matrix_room_id && (
                <span className="w-2 h-2 rounded-full bg-emerald-400" />
              )}
            </div>
          </Link>
        ))}
      </div>
    </div>
  )
}

7.3. Компонент MicroDAOAgentsSection

function MicroDAOAgentsSection({ agents }: { agents: Agent[] }) {
  return (
    <div className="glass-panel p-6">
      <h3 className="text-lg font-semibold text-white mb-4">
        <Bot /> Агенти MicroDAO
      </h3>
      <div className="space-y-2">
        {agents.map(agent => (
          <Link href={`/agents/${agent.id}`} key={agent.id}>
            <div className="flex items-center gap-3 p-2 hover:bg-white/5 rounded-lg">
              <div className="w-8 h-8 rounded-full bg-violet-500/30" />
              <div>
                <p className="text-sm text-white">{agent.name}</p>
                <p className="text-xs text-slate-400">{agent.role}</p>
              </div>
              <span className={`w-2 h-2 rounded-full ${
                agent.status === 'active' ? 'bg-emerald-400' : 'bg-slate-500'
              }`} />
            </div>
          </Link>
        ))}
      </div>
    </div>
  )
}

8. МОДУЛЬ 5 — SEED DATA

8.1. DAARION DAO (dao_daarion)

INSERT INTO city_rooms (id, slug, name, description, created_by, owner_type, owner_id, room_role, is_public, sort_order)
VALUES
  ('room_microdao_daarion-lobby', 'daarion-lobby', 'DAARION Lobby', 'Головна кімната DAARION DAO', 'u_system', 'microdao', 'dao_daarion', 'lobby', true, 10),
  ('room_microdao_daarion-governance', 'daarion-governance', 'Governance', 'Голосування та пропозиції', 'u_system', 'microdao', 'dao_daarion', 'governance', true, 20),
  ('room_microdao_daarion-operations', 'daarion-operations', 'Operations', 'Операційна діяльність', 'u_system', 'microdao', 'dao_daarion', 'operations', false, 30),
  ('room_microdao_daarion-knowledge', 'daarion-knowledge', 'Knowledge Base', 'Документація та FAQ', 'u_system', 'microdao', 'dao_daarion', 'knowledge', true, 40),
  ('room_microdao_daarion-treasury', 'daarion-treasury', 'Treasury', 'Фінанси та токеноміка', 'u_system', 'microdao', 'dao_daarion', 'treasury', false, 50),
  ('room_microdao_daarion-ai-core', 'daarion-ai-core', 'AI Core', 'Агенти та автоматизація', 'u_system', 'microdao', 'dao_daarion', 'ai-core', false, 60)
ON CONFLICT (slug) DO UPDATE SET
  name = EXCLUDED.name,
  room_role = EXCLUDED.room_role,
  owner_id = EXCLUDED.owner_id;

8.2. Districts (SOUL, GREENFOOD, ENERGYUNION)

Аналогічно для кожного District-а.


9. МОДУЛЬ 6 — MATRIX AUTO-CREATE

При створенні кімнати:

  1. Викликати ensure_room_has_matrix(slug, name, visibility)
  2. Отримати matrix_room_id
  3. Додати orchestrator агента до кімнати через join_user_to_room()
  4. Зберегти matrix_room_id в БД

10. SMOKE-ТЕСТИ

  1. /microdao/daarion:

    • Показує 6 кімнат
    • Кожна кімната має Matrix статус (зелена точка)
    • Клік → відкриває /city/daarion-lobby
  2. API:

    • GET /api/v1/microdao/daarion/rooms → 6 кімнат
    • GET /api/v1/microdao/daarion/agents → агенти DAO
  3. Chat Widget:

    • На сторінці MicroDAO працює чат для lobby
  4. Districts:

    • /microdao/soul, /microdao/greenfood, /microdao/energy-union
    • Мають свої кімнати

11. ФІНАЛЬНИЙ ЗВІТ

Після виконання створити:

docs/debug/microdao_rooms_integration_report_<DATE>.md

Зміст:

  • Список кімнат для кожного MicroDAO
  • API responses
  • Скріншоти/описи UI
  • Matrix статус кімнат

12. PROMPT ДЛЯ CURSOR

Виконай TASK_PHASE_MICRODAO_ROOMS_INTEGRATION_v1.md.

Фокус:
1) Backend: GET /api/v1/microdao/{slug}/rooms, /agents
2) repo_city: get_microdao_rooms, get_microdao_agents, create_microdao_room
3) Seed: 6 кімнат для DAARION, по 6 для кожного District
4) Frontend: MicroDAORoomsSection, MicroDAOAgentsSection
5) Matrix: auto-create для нових кімнат

Після завершення створи:
docs/debug/microdao_rooms_integration_report_<DATE>.md

Target Date: Immediate Priority: High Dependencies: District Portals complete, Matrix integration working