# Notely - Secure Multi-Space Note-Taking Application A production-ready, secure multi-tenant note-taking platform built with Go, Vue 3, and MongoDB. ## ๐Ÿš€ Quick Start ### Prerequisites - Docker & Docker Compose - Go 1.21+ (for local development) - Node.js 18+ (for frontend development) - MongoDB 7.0+ (for local development) ### Development with Docker Compose ```bash # Start all services docker-compose up # Backend: http://localhost:8080 # Frontend: http://localhost:5173 # MongoDB: localhost:27017 # Nginx: http://localhost:80 ``` ### Local Development Setup #### Backend ```bash cd backend # Install dependencies go mod download # Set environment variables export MONGODB_URI=mongodb://admin:password@localhost:27017/noteapp?authSource=admin export JWT_SECRET=your-secret-key export ENCRYPTION_KEY=00000000000000000000000000000000 # Run migrations and server go run ./cmd/server/main.go ``` #### Frontend ```bash cd frontend # Install dependencies npm install # Start development server npm run dev ``` ## ๐Ÿ“š Architecture ### Backend (GoClean Architecture) ``` backend/ โ”œโ”€โ”€ cmd/server/ # Entry point โ”œโ”€โ”€ internal/ โ”‚ โ”œโ”€โ”€ domain/ # Business logic (entities, interfaces) โ”‚ โ”œโ”€โ”€ application/ # Use cases (services, DTOs) โ”‚ โ”œโ”€โ”€ infrastructure/ # External dependencies (DB, auth) โ”‚ โ””โ”€โ”€ interfaces/ # API handlers & middleware โ”œโ”€โ”€ pkg/ # Public packages โ””โ”€โ”€ tests/ # Test suites ``` ### Frontend (Vue 3 Composition API) ``` frontend/ โ”œโ”€โ”€ src/ โ”‚ โ”œโ”€โ”€ components/ # Reusable Vue components โ”‚ โ”œโ”€โ”€ pages/ # Page components โ”‚ โ”œโ”€โ”€ stores/ # Pinia state management โ”‚ โ”œโ”€โ”€ services/ # API client โ”‚ โ”œโ”€โ”€ router/ # Vue Router config โ”‚ โ”œโ”€โ”€ assets/ # Styles and assets โ”‚ โ””โ”€โ”€ main.js # Entry point โ”œโ”€โ”€ index.html โ””โ”€โ”€ vite.config.js ``` ## ๐Ÿ” Security Features ### Authentication - **Argon2id password hashing** - Industry-standard PBKDF2 - **JWT tokens** with short expiration (1 hour) - **HTTP-only secure cookies** for refresh tokens - **CSRF protection** via SameSite cookies - **Brute-force protection** via login attempt tracking ### Authorization - **Role-based access control (RBAC)** per space: - Owner: Full control - Editor: Edit notes and categories - Viewer: Read-only access - **Space-level data isolation** - all queries include space_id - **IDOR prevention** - middleware enforces ownership verification ### Data Security - **Encryption at rest** for sensitive fields (OAuth secrets) - **HTTPS/TLS** in production (Nginx reverse proxy) - **Content Security Policy (CSP)** headers - **XSS protection** - DOMPurify for markdown sanitization - **SQL injection prevention** - parameterized queries (MongoDB) ### API Security - **Rate limiting** - IP-based and user-based - **Security headers** - HSTS, X-Frame-Options, X-Content-Type-Options - **CORS properly configured** - whitelist origin domains - **Input validation** on all endpoints ## ๐Ÿ“ฆ API Endpoints ### Authentication ``` POST /api/v1/auth/register - Register new user POST /api/v1/auth/login - Login user POST /api/v1/auth/refresh - Refresh access token POST /api/v1/auth/logout - Logout user GET /health - Health check ``` ### Spaces ``` GET /api/v1/spaces - List user's spaces POST /api/v1/spaces - Create space GET /api/v1/spaces/{spaceId} - Get space details PUT /api/v1/spaces/{spaceId} - Update space DELETE /api/v1/spaces/{spaceId} - Delete space ``` ### Notes ``` GET /api/v1/spaces/{spaceId}/notes - List notes POST /api/v1/spaces/{spaceId}/notes - Create note GET /api/v1/spaces/{spaceId}/notes/{noteId} - Get note PUT /api/v1/spaces/{spaceId}/notes/{noteId} - Update note DELETE /api/v1/spaces/{spaceId}/notes/{noteId} - Delete note GET /api/v1/spaces/{spaceId}/notes/search?q= - Search notes ``` ### Categories ``` GET /api/v1/spaces/{spaceId}/categories - List categories POST /api/v1/spaces/{spaceId}/categories - Create category PUT /api/v1/spaces/{spaceId}/categories/{id} - Update category DELETE /api/v1/spaces/{spaceId}/categories/{id} - Delete category ``` ## ๐Ÿ—„๏ธ Database Design ### MongoDB Collections #### users ```javascript { _id: ObjectId, email: String (unique), username: String (unique), password_hash: String, first_name: String, last_name: String, avatar: String, is_active: Boolean, email_verified: Boolean, created_at: Date, updated_at: Date, last_login_at: Date } ``` #### spaces ```javascript { _id: ObjectId, name: String, description: String, icon: String, owner_id: ObjectId, is_public: Boolean, created_at: Date, updated_at: Date } ``` #### memberships ```javascript { _id: ObjectId, user_id: ObjectId, space_id: ObjectId, role: String (owner|editor|viewer), joined_at: Date, invited_by: ObjectId, invited_at: Date } ``` #### notes ```javascript { _id: ObjectId, space_id: ObjectId, category_id: ObjectId, title: String, content: String (Markdown), tags: [String], is_pinned: Boolean, is_favorite: Boolean, created_by: ObjectId, updated_by: ObjectId, created_at: Date, updated_at: Date, viewed_at: Date } ``` #### categories ```javascript { _id: ObjectId, space_id: ObjectId, name: String, description: String, parent_id: ObjectId (for hierarchical structure), icon: String, order: Number, created_by: ObjectId, updated_by: ObjectId, created_at: Date, updated_at: Date } ``` #### Indexes ``` users: { email: 1 (unique), username: 1 (unique) } spaces: { owner_id: 1, created_at: -1 } memberships: { user_id: 1, space_id: 1 (unique), space_id: 1 } notes: { space_id: 1, category_id: 1, updated_at: -1, text: "text" } categories: { space_id: 1, parent_id: 1, order: 1 } ``` ## ๐Ÿณ Deployment ### Docker Compose (Development/Testing) ```bash docker-compose up -d ``` Services: - **MongoDB** (port 27017) - **Backend API** (port 8080) - **Frontend** (port 5173) - **Nginx Reverse Proxy** (port 80) ### Kubernetes (Production) ```bash # Create namespace and secrets kubectl apply -f devops/kubernetes/deployment.yaml # Verify deployment kubectl get pods -n noteapp kubectl port-forward svc/frontend 5173:5173 -n noteapp kubectl port-forward svc/backend 8080:8080 -n noteapp ``` Features: - **StatefulSet** for MongoDB with persistent storage - **Deployments** for backend and frontend with horizontal scaling - **Ingress** for routing (requires ingress controller) - **HPA** (Horizontal Pod Autoscaler) for automatic scaling - **Liveness & readiness probes** for health checks - **Resource limits** for fair resource allocation ## ๐Ÿงช Testing ### Backend Tests ```bash cd backend go test ./... go test -v ./tests/unit/... go test -v ./tests/integration/... ``` ### Frontend Tests ```bash cd frontend npm run test npm run test:watch ``` ## ๐Ÿ”ง Configuration ### Environment Variables #### Backend (.env) ``` MONGODB_URI=mongodb://admin:password@localhost:27017/noteapp JWT_SECRET=your-secret-key-min-32-chars ENCRYPTION_KEY=32-char-encryption-key-for-secrets PORT=8080 LOG_LEVEL=info ENV=development ``` #### Frontend (.env) ``` VITE_API_BASE_URL=http://localhost:8080 ``` ## ๐Ÿ“ Development Guidelines ### Code Structure - Follow clean architecture principles - Separate concerns: domain, application, infrastructure - Use interfaces for dependency injection - Keep services testable and focused ### Security Best Practices 1. **Never store secrets in code** - use environment variables 2. **Validate all inputs** on backend 3. **Sanitize outputs** before rendering 4. **Use HTTPS in production** 5. **Implement rate limiting** on APIs 6. **Log security events** (login attempts, permission denied) 7. **Audit trail** for sensitive operations ### Commit Message Format ``` [TYPE] Description types: feat, fix, docs, style, refactor, test, chore ``` ## ๐Ÿ“– API Documentation ### Request/Response Format All API requests and responses use JSON. ```bash # Example: Create Note curl -X POST http://localhost:8080/api/v1/spaces/{spaceId}/notes \ -H "Authorization: Bearer {accessToken}" \ -H "Content-Type: application/json" \ -d '{ "title": "My Note", "content": "# Markdown content", "tags": ["tag1", "tag2"], "category_id": null, "is_pinned": false, "is_favorite": false }' ``` ## ๐Ÿšจ Error Handling All errors return appropriate HTTP status codes: - `400` - Bad Request - `401` - Unauthorized - `403` - Forbidden (insufficient permissions) - `404` - Not Found - `409` - Conflict (e.g., duplicate email) - `429` - Too Many Requests (rate limit exceeded) - `500` - Internal Server Error ## ๐ŸŽฏ Future Enhancements - [ ] OAuth2/OIDC integration - [ ] Email notifications - [ ] Real-time collaboration (WebSockets) - [ ] Full-text search with Elasticsearch - [ ] Export to PDF/Markdown - [ ] Mobile applications - [ ] Plugin system - [ ] Advanced permissions management ## ๐Ÿ“„ License MIT License - See LICENSE file ## ๐Ÿ‘ฅ Contributing 1. Fork the repository 2. Create a feature branch 3. Commit your changes 4. Push to the branch 5. Create a Pull Request --- **Built with โค๏ธ for secure, collaborative note-taking**