init
This commit is contained in:
commit
ba1f43fd8e
35 changed files with 5926 additions and 0 deletions
364
README.md
Normal file
364
README.md
Normal file
|
@ -0,0 +1,364 @@
|
|||
# GoCheck - Collaborative Checklist Application
|
||||
|
||||
A real-time collaborative checklist application built with Go and React,
|
||||
featuring Server-Sent Events (SSE) for live updates and SQLite for data
|
||||
persistence.
|
||||
|
||||
## Features
|
||||
|
||||
- Create and manage checklists
|
||||
- Add, update, and delete checklist items
|
||||
- Real-time collaboration with Server-Sent Events
|
||||
- Item locking mechanism to prevent conflicts
|
||||
- Hierarchical items (parent-child relationships)
|
||||
- SQLite database for data persistence
|
||||
- **Modern web frontend with React and TypeScript**
|
||||
- **Real-time updates across multiple browser tabs/windows**
|
||||
- **SSE-first architecture: All data flows through Server-Sent Events**
|
||||
|
||||
## Architecture
|
||||
|
||||
### SSE-First Design
|
||||
|
||||
This application follows an **SSE-first architecture** where all checklist data
|
||||
flows through Server-Sent Events:
|
||||
|
||||
- **No API calls for data retrieval**: The frontend never calls the
|
||||
`/api/checklists/{uuid}/items` endpoint
|
||||
- **SSE as primary data source**: All checklist items are received via SSE
|
||||
streaming
|
||||
- **Real-time state management**: The frontend maintains state purely through
|
||||
SSE events
|
||||
- **Immediate updates**: Changes appear instantly across all connected clients
|
||||
|
||||
#### Data Flow
|
||||
|
||||
1. **Initial Connection**: When a client connects to a checklist, the SSE
|
||||
endpoint sends the complete current state
|
||||
2. **Real-time Updates**: All subsequent changes (add, update, delete, lock) are
|
||||
broadcast via SSE
|
||||
3. **State Synchronization**: The frontend updates its local state based on SSE
|
||||
events without API calls
|
||||
|
||||
This design ensures:
|
||||
|
||||
- **Consistency**: All clients see the same data at the same time
|
||||
- **Performance**: No unnecessary API calls to reload data
|
||||
- **Real-time Experience**: Changes appear instantly across all connected
|
||||
browsers
|
||||
- **Scalability**: Reduces server load by eliminating polling
|
||||
|
||||
## Prerequisites
|
||||
|
||||
- Go 1.16 or later
|
||||
- SQLite3 (usually included with Go)
|
||||
|
||||
## Setup
|
||||
|
||||
1. **Initialize the Go module** (already done):
|
||||
```bash
|
||||
go mod init gocheck
|
||||
```
|
||||
|
||||
2. **Install dependencies**:
|
||||
```bash
|
||||
go mod tidy
|
||||
```
|
||||
|
||||
3. **Build the application**:
|
||||
```bash
|
||||
go build
|
||||
```
|
||||
|
||||
4. **Run the server**:
|
||||
```bash
|
||||
./gocheck
|
||||
```
|
||||
|
||||
Or use the demo script for a guided experience:
|
||||
```bash
|
||||
./demo.sh
|
||||
```
|
||||
|
||||
The server will start on `http://localhost:8080`
|
||||
|
||||
## Deployment
|
||||
|
||||
The application is built as a single binary with embedded static files, making
|
||||
deployment simple:
|
||||
|
||||
- **Single Executable**: The `gocheck` binary contains all necessary files
|
||||
- **No External Dependencies**: Just copy the binary to your server
|
||||
- **Cross-Platform**: Build for different platforms as needed
|
||||
|
||||
### Binary Deployment
|
||||
|
||||
To build for different platforms:
|
||||
|
||||
```bash
|
||||
# Linux
|
||||
GOOS=linux GOARCH=amd64 go build -o gocheck-linux
|
||||
|
||||
# Windows
|
||||
GOOS=windows GOARCH=amd64 go build -o gocheck.exe
|
||||
|
||||
# macOS
|
||||
GOOS=darwin GOARCH=amd64 go build -o gocheck-macos
|
||||
```
|
||||
|
||||
### Container Deployment
|
||||
|
||||
The application includes a multi-stage Containerfile for containerized
|
||||
deployment:
|
||||
|
||||
#### Using Podman (Recommended)
|
||||
|
||||
```bash
|
||||
# Build and run with the provided script
|
||||
./build-container.sh
|
||||
|
||||
# Or manually:
|
||||
podman build -t gocheck -f Containerfile .
|
||||
podman run -d --name gocheck-container -p 8080:8080 -v gocheck-data:/app gocheck
|
||||
|
||||
# With custom port:
|
||||
PORT=3000 ./build-container.sh
|
||||
# Or manually:
|
||||
podman run -d --name gocheck-container -p 3000:8080 -e PORT=8080 -v gocheck-data:/app gocheck
|
||||
```
|
||||
|
||||
#### Using Docker
|
||||
|
||||
```bash
|
||||
# Build the image
|
||||
docker build -t gocheck -f Containerfile .
|
||||
|
||||
# Run the container
|
||||
docker run -d --name gocheck-container -p 8080:8080 -v gocheck-data:/app gocheck
|
||||
|
||||
# With custom port:
|
||||
docker run -d --name gocheck-container -p 3000:8080 -e PORT=8080 -v gocheck-data:/app gocheck
|
||||
```
|
||||
|
||||
#### Container Features
|
||||
|
||||
- **Multi-stage build**: Uses Go Alpine for building, distroless for runtime
|
||||
- **Minimal footprint**: Runtime container is only ~2MB
|
||||
- **Persistent data**: SQLite database is stored in a named volume
|
||||
- **Security**: Runs as non-root user in distroless container
|
||||
- **Configurable**: Supports environment variables for customization
|
||||
|
||||
#### Environment Variables
|
||||
|
||||
- `PORT`: Set the port the application listens on (default: 8080)
|
||||
```bash
|
||||
# Example: Run on port 3000
|
||||
PORT=3000 ./build-container.sh
|
||||
```
|
||||
|
||||
## Frontend
|
||||
|
||||
The application includes a modern web frontend built with **React**:
|
||||
|
||||
- **Single Page Application**: No page reloads needed
|
||||
- **Home Page**: Welcome page for creating new checklists
|
||||
- **Checklist Page**: Dedicated page for viewing and editing checklists
|
||||
- **Local Storage**: Automatically saves and lists your checklists
|
||||
- **Real-time Updates**: Changes appear instantly across all connected browsers
|
||||
- **Responsive Design**: Works on desktop and mobile devices
|
||||
- **Item Locking**: Visual indicators when items are being edited
|
||||
- **Hierarchical Items**: Support for parent-child relationships
|
||||
- **Modern UI**: Clean, intuitive interface
|
||||
- **TypeScript**: Full type safety and better developer experience
|
||||
- **Component-based**: Modular, maintainable code structure
|
||||
- **URL-based Routing**: Share checklist URLs directly
|
||||
- **ESLint**: Code quality enforcement with no-semicolon style
|
||||
|
||||
### Frontend Development
|
||||
|
||||
The frontend is located in the `frontend/` directory and uses:
|
||||
|
||||
- **React**: Modern JavaScript library for building user interfaces
|
||||
- **TypeScript**: Type-safe JavaScript
|
||||
- **Vite**: Fast build tool and dev server
|
||||
- **CSS Modules**: Scoped styling
|
||||
|
||||
#### Development Commands
|
||||
|
||||
```bash
|
||||
# Install dependencies
|
||||
cd frontend && npm install
|
||||
|
||||
# Start development server (with API proxy)
|
||||
cd frontend && npm run dev
|
||||
|
||||
# Build for production
|
||||
cd frontend && npm run build
|
||||
|
||||
# Lint code (check for issues)
|
||||
cd frontend && npm run lint
|
||||
|
||||
# Lint and auto-fix issues
|
||||
cd frontend && npm run lint:fix
|
||||
|
||||
# Build frontend and copy to static directory
|
||||
./build-frontend.sh
|
||||
```
|
||||
|
||||
#### Development Workflow
|
||||
|
||||
1. Start the backend server: `./gocheck`
|
||||
2. Start the frontend dev server: `cd frontend && npm run dev`
|
||||
3. Access the app at: `http://localhost:5173` (frontend dev server)
|
||||
4. The frontend will proxy API requests to the backend at
|
||||
`http://localhost:8080`
|
||||
|
||||
Simply open `http://localhost:8080` in your browser to use the production
|
||||
application.
|
||||
|
||||
#### Page Structure
|
||||
|
||||
- **Home Page** (`/`): Welcome page with option to create new checklists and
|
||||
view saved checklists
|
||||
- **Checklist Page** (/{uuid}`): View and edit specific checklists
|
||||
- when opening this route and that checklistid is not yet saved into
|
||||
localstorage it should be committed there
|
||||
- **URL Sharing**: Share checklist URLs directly with others for collaboration
|
||||
- **Local Storage**: Checklists are automatically saved and can be renamed or
|
||||
removed from the home page
|
||||
|
||||
## API Endpoints
|
||||
|
||||
### Checklists
|
||||
|
||||
- `POST /api/checklists` - Create a new checklist
|
||||
- `POST /api/checklists/{uuid}/items` - Add an item to a checklist
|
||||
- `PATCH /api/checklists/{uuid}/items/{id}` - Update an item
|
||||
- `DELETE /api/checklists/{uuid}/items/{id}` - Delete an item
|
||||
- `POST /api/checklists/{uuid}/items/{id}/lock` - Lock an item for editing
|
||||
- `GET /api/checklists/{uuid}/sse` - Server-Sent Events stream for real-time
|
||||
updates (primary data source)
|
||||
|
||||
**Note**: The `GET /api/checklists/{uuid}/items` endpoint exists but is not used
|
||||
by the frontend. All data flows through the SSE endpoint for real-time updates.
|
||||
|
||||
### API Response Format
|
||||
|
||||
All API endpoints return JSON responses with a consistent format:
|
||||
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"message": "Operation completed successfully"
|
||||
// ... additional data specific to the endpoint
|
||||
}
|
||||
```
|
||||
|
||||
#### Example Responses
|
||||
|
||||
**Create Checklist:**
|
||||
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"message": "Checklist created successfully",
|
||||
"uuid": "123e4567-e89b-12d3-a456-426614174000"
|
||||
}
|
||||
```
|
||||
|
||||
**Add Item:**
|
||||
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"message": "Item added successfully",
|
||||
"item": {
|
||||
"id": 1,
|
||||
"content": "New item",
|
||||
"checked": false,
|
||||
"parent_id": null,
|
||||
"checklist_uuid": "123e4567-e89b-12d3-a456-426614174000"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**Update Item:**
|
||||
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"message": "Item updated successfully",
|
||||
"item": {
|
||||
"id": 1,
|
||||
"content": "Updated content",
|
||||
"checked": true,
|
||||
"parent_id": null,
|
||||
"checklist_uuid": "123e4567-e89b-12d3-a456-426614174000"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**Delete Item:**
|
||||
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"message": "Item deleted successfully",
|
||||
"id": 1
|
||||
}
|
||||
```
|
||||
|
||||
**Lock Item:**
|
||||
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"message": "Item locked successfully",
|
||||
"id": 1,
|
||||
"locked_by": "user123",
|
||||
"expires": "2024-01-01T12:00:00Z"
|
||||
}
|
||||
```
|
||||
|
||||
**Get Items:**
|
||||
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"message": "Items loaded successfully",
|
||||
"items": [
|
||||
{
|
||||
"id": 1,
|
||||
"content": "Item 1",
|
||||
"checked": false,
|
||||
"parent_id": null,
|
||||
"checklist_uuid": "123e4567-e89b-12d3-a456-426614174000"
|
||||
}
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
## Dependencies
|
||||
|
||||
- `github.com/google/uuid` - UUID generation
|
||||
- `github.com/mattn/go-sqlite3` - SQLite driver for Go
|
||||
|
||||
## Database
|
||||
|
||||
The application uses SQLite with the following schema:
|
||||
|
||||
- `checklists` table: Stores checklist metadata
|
||||
- `items` table: Stores checklist items with hierarchical relationships
|
||||
|
||||
## Real-time Features
|
||||
|
||||
- **SSE-first architecture**: All data flows through Server-Sent Events
|
||||
- **Real-time state synchronization**: No API polling required
|
||||
- **Item locking with automatic expiration** (30 seconds)
|
||||
- **Broadcast updates to all connected clients**
|
||||
- **Immediate UI updates**: Changes appear instantly across all browsers
|
||||
|
||||
## Development
|
||||
|
||||
To run in development mode with automatic reloading, you can use tools like
|
||||
`air` or `realize`.
|
Loading…
Add table
Add a link
Reference in a new issue