Skip to content
Merged
Show file tree
Hide file tree
Changes from 2 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
16 changes: 16 additions & 0 deletions .cursor/rules/alembic-no-auto-migrations.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
---
description: Do not create Alembic migration files; the user creates them manually
globs: api/app/**/*.py
alwaysApply: true
---

# Alembic Migrations

**Do not create migration files.** The user manages Alembic migrations manually.

## Workflow

- When adding or changing SQLAlchemy models (columns, tables, indexes), update the model code only.
- Do **not** create new files in `alembic/versions/`.
- Do **not** run `alembic revision` or `alembic upgrade`.
- After model changes, tell the user to run: `alembic revision --autogenerate -m "description"` and `alembic upgrade head`.
Comment thread
martian56 marked this conversation as resolved.
Outdated
14 changes: 14 additions & 0 deletions .cursor/rules/api-authentication.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
---
description: JWT authentication and password security
globs: api/app/**/*
alwaysApply: false
---

# Authentication

## Requirements

- **JWT** for authentication.
- **bcrypt** for password hashing.
- **Never store plaintext passwords.**
- **Protected routes** must require authentication.
37 changes: 37 additions & 0 deletions .cursor/rules/api-boards-elements.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
---
description: Boards and canvas elements data model
globs: api/app/**/*
alwaysApply: false
---

# Boards and Elements

**Boards** are collaborative canvases. Each board contains many **elements**.

## Element Types

- Shapes
- Sticky notes
- Text
- Arrows
- Connectors

## Storage

Store element properties as **JSONB** in PostgreSQL.

Example element data:

```json
{
"x": 120,
"y": 240,
"width": 300,
"height": 120,
"text": "Hello"
}
```

## API Design

Design the API so that **updates to elements can be frequent and efficient** (e.g. bulk updates, delta sync, or patch endpoints).
31 changes: 31 additions & 0 deletions .cursor/rules/api-database-conventions.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
---
description: PostgreSQL, SQLAlchemy, and Alembic conventions
globs: api/app/**/*
alwaysApply: false
---

# Database Conventions

The project uses **PostgreSQL** with **SQLAlchemy** and **Alembic**.

## Model Changes Workflow

1. Ensure the SQLAlchemy model is correct.
2. Generate an Alembic migration reflecting the change.
3. Migrations must be **idempotent and safe**.
Comment thread
martian56 marked this conversation as resolved.
Outdated

## Database Rules

| Rule | Details |
|------|---------|
| **Primary keys** | Use UUID |
| **Naming** | snake_case in the database |
| **Timestamps** | Include `created_at` and `updated_at` |
| **Indexes** | Add indexes for frequently queried columns |

## Example Indexed Columns

- `users.email`
- `users.username`
- `boards.workspace_id`
- `elements.board_id`
27 changes: 27 additions & 0 deletions .cursor/rules/api-layer-responsibilities.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
---
description: API layer flow and responsibility separation
globs: api/app/**/*
alwaysApply: false
---

# API Layer Architecture

All backend features follow this flow:

```
router → service → repository → database
```

## Responsibilities

| Layer | File | Responsibility |
|-------|------|----------------|
| **router** | `router.py` | HTTP requests and responses only |
| **service** | `service.py` | Business logic |
| **repository** | `repository.py` | Database access via SQLAlchemy |
| **schemas** | `schemas.py` | Request/response models (Pydantic) |
| **model** | `model.py` | SQLAlchemy database models |

## Rule

**Never mix these responsibilities.** Each layer has a single concern.
27 changes: 27 additions & 0 deletions .cursor/rules/api-modular-architecture.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
---
description: API modular architecture and workflow
globs: api/app/**/*
alwaysApply: false
---

# API Architecture – Modular Structure

Before generating or modifying any API code, **read the entire `api/app` directory** and understand the existing folder and module structure.

## Module Layout

Each feature lives in `app/modules/<feature>/`. Every module typically contains:

| File | Purpose |
|------|---------|
| `router.py` | HTTP endpoints |
| `service.py` | Business logic |
| `repository.py` | Data access |
| `schemas.py` | Pydantic request/response models |
| `model.py` | SQLAlchemy model(s) |

## Rules

- **Never introduce a different structure.** Follow this layout exactly.
- **Extend existing modules** when adding functionality—don’t create unrelated folders.
- **When unsure where code belongs**, inspect similar modules and mirror their structure.
28 changes: 28 additions & 0 deletions .cursor/rules/api-realtime-websockets.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
---
description: Real-time collaboration and WebSocket events
globs: api/app/**/*
alwaysApply: false
---

# Real-Time Collaboration

Loomy supports **real-time collaboration**. Board updates should eventually be **broadcast through WebSockets**.

## API Endpoints

Support these operations for elements:

- **Creating** elements
- **Updating** elements
- **Deleting** elements

## WebSocket Events

Events to broadcast:

| Event | Purpose |
|-------|---------|
| `element.created` | New element added |
| `element.updated` | Element changed |
| `element.deleted` | Element removed |
| `cursor.moved` | User cursor position |
18 changes: 18 additions & 0 deletions .cursor/rules/api-redis.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
---
description: Redis usage for real-time, caching, and rate limiting
globs: api/app/**/*
alwaysApply: false
---

# Redis

Redis is used for:

- **WebSocket pub/sub**
- **Presence tracking**
- **Caching**
- **Rate limiting**

## Real-Time and Event Broadcasting

When implementing **real-time collaboration** or **event broadcasting**, use **Redis pub/sub**—not direct in-memory communication.
32 changes: 32 additions & 0 deletions .cursor/rules/api-rest-conventions.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
---
description: REST API conventions and response schemas
globs: api/app/**/*
alwaysApply: false
---

# REST API Conventions

All APIs must follow REST best practices.

## Endpoint Conventions

| Method | Path | Purpose |
|--------|------|---------|
| GET | `/api/resource` | List resources |
| GET | `/api/resource/{id}` | Get by ID |
| POST | `/api/resource` | Create |
| PATCH | `/api/resource/{id}` | Update |
| DELETE | `/api/resource/{id}` | Delete |

## Pagination

Use pagination for list endpoints:

```
GET /api/boards?page=1&limit=20
```

## Response Schemas

- **Never return database models directly.**
- **Always return Pydantic response schemas.**
24 changes: 24 additions & 0 deletions .cursor/rules/excalidraw-canvas.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
---
description: Use Excalidraw for the whiteboard canvas and research its APIs before making canvas changes
globs: apps/frontend/src/**
alwaysApply: false
---

# Excalidraw Canvas & Research Rule

- **Use `@excalidraw/excalidraw` for the board/canvas UI**:
- When implementing or updating any whiteboard, board, or drawing canvas in the frontend, prefer the official Excalidraw React component and APIs (`Excalidraw`, `initialData`, `onChange`, `excalidrawAPI`, `UIOptions`, `theme`, etc.).
- Avoid building a custom canvas/interaction system from scratch unless there is a very strong, documented reason.

- **Deep research before significant changes**:
- Before introducing or modifying core canvas behavior (selection, tools, sidebar, persistence, multi-user cursors, etc.), the agent should:
- Review the latest [Excalidraw docs](https://docs.excalidraw.com) and API (props, `excalidrawAPI`, `restore`, `sceneCoordsToViewportCoords`, etc.).
- Look for recommended patterns (initialData, onChange, updateScene, CSS variable overrides) in Excalidraw’s documentation.
- Align implementations with those patterns where practical.

- **Integration expectations**:
- Canvas state (elements + appState) should be persisted via the backend’s elements API (`excalidraw_snapshot` type) and synced in real time via WebSocket when needed.
- Keep the server-side boards/elements model aligned with Excalidraw’s scene data (elements array + appState object).

- **When in doubt**:
- If unsure how to implement a canvas feature, explore the Excalidraw docs and examples first, summarize options, then choose the approach that best fits Loomy’s backend and real-time architecture.
9 changes: 9 additions & 0 deletions .cursor/rules/extend-dont-abstract.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
---
description: Prefer extending modules over new abstractions
alwaysApply: true
---

# Code Generation Preference

- **Extend existing modules** instead of creating new abstractions.
- Goal: **maintainability and readability** for an open-source project.
34 changes: 34 additions & 0 deletions .cursor/rules/loomy-project-context.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
---
description: Loomy project context and API requirements
alwaysApply: true
---

# Loomy – Project Context

Loomy is an open-source, self-hostable collaborative whiteboard similar to Miro.

## User Capabilities

- Create workspaces and boards
- Collaborate in real time on infinite canvas boards
- Place elements: shapes, text, connectors, sticky notes
- Invite other users and work together

## Backend API Requirements

The API must support:

| Domain | Requirements |
|--------|--------------|
| **Authentication** | Auth flows, sessions, tokens |
| **User accounts** | CRUD, profiles, identity |
| **Workspaces** | Multi-tenant workspaces, membership |
| **Boards** | Boards per workspace, metadata |
| **Board elements** | Shapes, text, connectors, sticky notes |
| **Real-time collaboration** | WebSockets or similar for live updates |
| **Permissions** | Access control for workspaces, boards, elements |

## Design Principles

- **Scalability**: Boards may contain many elements; design for large datasets and pagination.
- **Concurrency**: Support multiple concurrent users per board; consider optimistic locking, conflict resolution, or CRDTs for real-time sync.
20 changes: 20 additions & 0 deletions .cursor/rules/loomy-tech-stack.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
---
description: Loomy recommended tech stack – Zustand, Yjs, Excalidraw, FastAPI
alwaysApply: true
---

# Loomy Tech Stack

Use this stack for new features and architectural decisions:

| Layer | Technology |
|-------|------------|
| **UI State** | Zustand |
| **Realtime Collaboration** | Yjs |
| **Canvas Engine** | Excalidraw |
| **Backend** | FastAPI |

- Prefer **Zustand** over Redux, Context, or ad-hoc useState for shared UI state.
- Use **Yjs** for collaborative sync (cursors, presence, document state) when applicable.
- Use **Excalidraw** (`@excalidraw/excalidraw`) for the whiteboard canvas; persist scene as `excalidraw_snapshot` (elements + appState) via the elements API.
- Keep the **FastAPI** backend; do not introduce other backend frameworks.
15 changes: 15 additions & 0 deletions .cursor/rules/python-standards.mdc
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
---
description: Python coding standards
globs: **/*.py
alwaysApply: false
---

# Python Standards

- Follow **modern Python practices**.
- Use **type hints everywhere**.
- Keep functions **small and focused**.
- **Avoid duplicated logic** (extract helpers, reuse).
- Use **dependency injection** for database sessions.

**Prefer clarity over cleverness.**
Loading
Loading