Files
hyprcrd/README.md
T
2026-04-08 14:04:23 +02:00

231 lines
6.8 KiB
Markdown

# hyprcrd
A self-hosted card/note manager with markdown, tags, image galleries, and Obsidian-compatible export.
## Requirements
- PHP 8.3+
- Apache with `mod_rewrite`
- PHP extensions: `pdo_sqlite`, `zip`
No external dependencies. All assets are bundled locally.
## Quick Start (Docker)
```bash
git clone https://git.uesome.de/tanztee/hyprcrd.git
cd hyprcrd
docker build -t hyprcrd .
docker run -d -p 8080:80 -v hyprcrd-data:/var/www/html/data hyprcrd
```
Open `http://localhost:8080` and set your password on first visit.
The `-v hyprcrd-data:/var/www/html/data` flag persists the database across container restarts.
## Manual Installation
### 1. Clone
```bash
git clone https://git.uesome.de/tanztee/hyprcrd.git
cd hyprcrd
```
### 2. Set document root
Point your web server's document root to the `public/` directory.
**Apache vhost example:**
```apache
<VirtualHost *:80>
ServerName hyprcrd.local
DocumentRoot /path/to/hyprcrd/public
<Directory /path/to/hyprcrd/public>
AllowOverride All
Require all granted
</Directory>
</VirtualHost>
```
Make sure `mod_rewrite` is enabled:
```bash
a2enmod rewrite
systemctl restart apache2
```
### 3. Set permissions
```bash
mkdir -p data public/uploads
chmod 755 data
chmod 777 public/uploads
```
The web server user (e.g. `www-data`) needs write access to both directories.
### 4. PHP settings (optional)
For larger image uploads, adjust in `php.ini`:
```ini
upload_max_filesize = 20M
post_max_size = 22M
```
### 5. Open and set password
Navigate to your URL. On first visit, you'll be prompted to set a password (min. 4 characters). That's it.
## Directory Structure
```
hyprcrd/
├── config.php # App constants (auto-configured)
├── Dockerfile
├── docker-entrypoint.sh
├── src/
│ ├── bootstrap.php # Initialization
│ └── Database.php # SQLite schema & migrations
├── public/ # Document root
│ ├── index.php # Entry point & API
│ ├── .htaccess # URL rewriting
│ ├── css/
│ │ ├── style.css # App styles
│ │ ├── tailwind.out.css # Generated Tailwind utilities
│ │ ├── fonts.css # Local @font-face rules
│ │ └── vendor/ # Phosphor Icons CSS + fonts
│ ├── fonts/ # JetBrains Mono & Silkscreen
│ ├── js/
│ │ ├── app.js # Orchestrator
│ │ ├── modules/ # Feature modules
│ │ └── vendor/ # marked.js, DOMPurify
│ └── uploads/ # User media (writable)
└── data/
└── hyprcrd.db # SQLite database (auto-created)
```
## Features
- **Cards** with markdown body, color, tags, and position
- **Buckets** for organizing cards into groups
- **Tags** written as `#tagname` or hierarchical `#parent/child` in card body, extracted automatically
- **Markdown** with `[[Card Title]]` wiki-links, ```` ```gallery ```` image galleries, ```` ```tree ```` list views
- **Search** combining text and `#tag` filters (e.g. `#project meeting notes`)
- **Image gallery** with orphan detection and fullscreen viewer
- **Split view** showing tag-related and content-related cards
- **Import/Export** as JSON+media ZIP or Obsidian/Logseq-compatible markdown vault
- **Drag & drop** card reordering and grouping
- **Calendar** with month view, journal entries, appointments, and day popup
- **CalDAV sync** with ownCloud/Nextcloud (bidirectional, `#termin` tagged cards)
- **Inline calculator** (`?3+5` → `8`, `34+56?` → `34+56=90`)
- **Snippets** (`?dat`, `?time`, `?now`, `?todo`, `?table`, `?code`, ...)
- **Keyboard shortcuts**: `Ctrl+K` search, `F1` help, `Shift+scroll` zoom, arrow keys in autocomplete
## Data & Backup
All data lives in two places:
- `data/hyprcrd.db` — SQLite database (cards, buckets, settings)
- `public/uploads/` — uploaded images and audio
Back up both to preserve everything. The database auto-migrates on startup.
## Export Formats
- **JSON export** (`export` button) — full backup with media, re-importable
- **Markdown vault** (`vault` button) — Obsidian/Logseq-compatible structure:
```
Bucket Name/
Card Title.md # YAML frontmatter + markdown body
attachments/
image.jpg
```
## CalDAV Sync (ownCloud / Nextcloud)
hyprcrd can sync appointment cards with any CalDAV server (tested with ownCloud 10.15.3.0).
### Setup
1. Open the **calendar** (button in header)
2. Click the **gear icon** in the calendar header
3. Enter your CalDAV URL, username, and app password:
```
URL: https://cloud.example.com/remote.php/dav/calendars/your-user/personal/
Username: your-user
Password: your-app-password
```
4. Click **test** to verify the connection
5. Click **save**
### How it works
- Cards tagged with `#termin` are synced as calendar events
- The appointment card template maps to iCalendar fields:
```markdown
Title: 2026-04-15 — Team Meeting
**Zeit:** 14:30-15:30
**Ort:** Room 42
**Teilnehmer:** Alice, Bob
---
**Notizen:**
Agenda items here
#termin
```
- **Sync is bidirectional**: local changes push to the server, remote changes pull to hyprcrd
- **Conflict resolution**: last-modified timestamp wins
- **Deleted cards**: tracked via tombstones, deleted on the server on next sync
- **Auto-sync**: triggers when opening the calendar (max once per minute)
- **Manual sync**: click the cloud icon in the calendar header
### Security
- Credentials are encrypted at rest (AES-256-CBC) in the SQLite database
- All sync operations run server-side (PHP/cURL), no client-side credential exposure
- Supports HTTPS with certificate verification
## Calendar
The built-in calendar shows cards on their dates:
- **Journal cards** (title = `2026-04-08`) appear on that date
- **Appointment cards** (title = `2026-04-08 — Subject`) appear on their date
- **Other cards** fall back to their creation date
- **Click a day** to see all cards in a popup
- **Double-click** or use **+ journal** / **+ termin** to create new entries
- Appointment template includes Zeit, Ort, Teilnehmer, Notizen fields
- Navigate months with arrow buttons, **today** jumps to current date
## Rebuilding Tailwind CSS
After changing Tailwind utility classes in HTML or JS files:
```bash
# Download standalone CLI (once)
curl -sL https://github.com/tailwindlabs/tailwindcss/releases/latest/download/tailwindcss-linux-x64 -o tailwindcss && chmod +x tailwindcss
# Build
./tailwindcss --input public/css/tailwind.css --output public/css/tailwind.out.css --content "public/index.php,public/js/**/*.js" --minify
```
## Security
- Bcrypt password hashing
- CSRF protection on all mutations
- Rate-limited login (5 attempts/60s)
- Upload directory blocks PHP execution
- DOMPurify sanitizes all rendered markdown
- Security headers (X-Frame-Options, HSTS, etc.)
## License
MIT