Commit graph

77 commits

Author SHA1 Message Date
ef5d2dcfcf feat: wire Nostr subscription sync into extension lifecycle
Some checks failed
lint.yml / feat: wire Nostr subscription sync into extension lifecycle (pull_request) Failing after 0s
lint.yml / feat: wire Nostr subscription sync into extension lifecycle (push) Failing after 0s
v1.2.1-aio.2
Add background task that subscribes to kind 31922/31923 events
from relays and processes them into the local database. Starts
15s after NostrClient connects (sequenced after publish client).

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 18:30:00 +02:00
e937883564 feat: add NIP-52 event sync from Nostr relays
Subscribe to kind 31922/31923 events and upsert into local DB:
- New events discovered from relays are auto-approved
- Existing events are updated if incoming version is newer
- Deduplication via event ID and d-tag correlation
- Events from Nostr have empty wallet (not ticketed locally)

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 18:29:14 +02:00
1bddb99132 feat: upgrade NostrClient to bidirectional (publish + subscribe)
Add receive queue, subscription management, and event deduplication
to support incoming NIP-52 calendar events from relays.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 18:28:21 +02:00
4d91426e82 refactor: consolidate create and propose endpoints into single POST /events
Some checks failed
lint.yml / refactor: consolidate create and propose endpoints into single POST /events (pull_request) Failing after 0s
Remove separate /events/propose endpoint. POST /events now uses
invoice key (any user) and determines approval status based on:
- LNbits admin → auto-approved
- auto_approve setting → auto-approved
- Otherwise → proposed (requires admin approval)

Separate PUT /events/{id} for updates (admin key, event owner).

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 18:24:10 +02:00
b4d7653988 fix: check auto_approve setting in propose endpoint
Some checks failed
lint.yml / fix: check auto_approve setting in propose endpoint (pull_request) Failing after 0s
The propose endpoint always set status to 'proposed' regardless of
the auto_approve setting. Now checks the setting and auto-approves
(+ publishes to Nostr) when enabled.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 18:16:43 +02:00
29045163a3 feat: add location and categories fields, simplify event creation
Some checks failed
lint.yml / feat: add location and categories fields, simplify event creation (pull_request) Failing after 0s
- Add location (text) and categories (JSON list) to Event model
- Make most CreateEvent fields optional: only title + start date required
- Default end_date to start_date, closing_date to end_date
- Categories stored as JSON text, parsed via validator
- NIP-52 publisher includes location tag and t tags for categories
- Migration m011 adds location and categories columns

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 18:05:25 +02:00
d69ec7dda2 feat: add admin-toggleable auto-approve setting
Some checks failed
lint.yml / feat: add admin-toggleable auto-approve setting (pull_request) Failing after 0s
- Extension settings table with auto_approve boolean
- GET/PUT /api/v1/settings endpoints (LNbits admin only)
- Settings card in admin UI with toggle
- When auto_approve is enabled, non-admin events skip approval

Closes aiolabs/events#11

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 17:59:59 +02:00
2db0102857 feat: publish NIP-52 events on approve/create/update/cancel/delete
Some checks failed
lint.yml / feat: publish NIP-52 events on approve/create/update/cancel/delete (pull_request) Failing after 0s
- On approve: publish kind 31922 calendar event to Nostr
- On admin create (auto-approved): publish immediately
- On update (approved event): republish (kind 31922 is replaceable)
- On cancel/delete: publish kind 5 delete event
- All Nostr calls are wrapped in try/except for graceful degradation
- Event creator's Account keypair used for signing

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 17:24:17 +02:00
e8fcecac40 feat: wire NostrClient into events extension lifecycle
Start a publish-only NostrClient as a background task (10s delay
for nostrclient readiness). Graceful degradation: if nostrclient
is unavailable, events extension continues without Nostr publishing.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 17:21:28 +02:00
5013709be7 feat: add NIP-52 calendar event builder and publisher
- build_nip52_event(): Event model → kind 31922 NostrEvent with
  d, title, start, end, image tags
- build_nip52_delete_event(): kind 5 delete with 'a' tag per NIP-09
- sign_nostr_event(): Schnorr signing via coincurve
- publish_event_to_nostr(): build + sign + publish, returns event
  for metadata storage. Graceful failure (returns None).

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 17:14:22 +02:00
f76e21e960 feat: add Nostr event tracking columns to events table
Migration m009 adds nostr_event_id and nostr_event_created_at to
track published NIP-52 calendar events. Enables correlation between
LNbits events and their Nostr representations.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 17:13:36 +02:00
f965cf07c9 feat: add publish-only NostrClient and NostrEvent model
Stripped-down Nostr client that connects to nostrclient's internal
WebSocket for publishing NIP-52 calendar events. No subscription
capabilities — publish queue only.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 17:11:55 +02:00
1ad99aa3d6 fix: hide approve/reject buttons for non-admin users
Some checks failed
lint.yml / fix: hide approve/reject buttons for non-admin users (pull_request) Failing after 0s
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 11:45:08 +02:00
920125aaee feat: auto-propose events from non-admin users
Some checks failed
lint.yml / feat: auto-propose events from non-admin users (pull_request) Failing after 0s
Events created by non-admin users via POST /events are now set to
'proposed' status, requiring LNbits admin approval. Admin-created
events are auto-approved.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 11:39:01 +02:00
ba97205592 feat: separate admin view into own events and all users' events
Some checks failed
lint.yml / feat: separate admin view into own events and all users' events (pull_request) Failing after 0s
Admin sees two tables: "Events" (own wallet events) and "All Users'
Events" (events from other users' wallets, admin only). Non-admin
users only see their own events table.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 11:34:59 +02:00
c1e66fbf7f fix: use check_admin for approval endpoints, not require_admin_key
Some checks failed
lint.yml / fix: use check_admin for approval endpoints, not require_admin_key (pull_request) Failing after 0s
require_admin_key only checks that the API key is a wallet admin key,
which ANY user has. check_admin verifies the user is a LNbits admin
(super_user or lnbits_admin_users). JS updated to omit API key on
admin endpoints, relying on session cookie auth instead.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 11:27:21 +02:00
7843da21d8 feat: add admin endpoint to view all events across wallets
Some checks failed
lint.yml / feat: add admin endpoint to view all events across wallets (pull_request) Failing after 0s
- GET /api/v1/events/all — returns all events regardless of wallet (admin key)
- Admin UI tries /events/all first, falls back to own wallet events
- Approved events from other users now visible in admin events table

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 11:19:21 +02:00
b467826622 fix: fetch pending events separately from admin's own events
Some checks failed
lint.yml / fix: fetch pending events separately from admin's own events (pull_request) Failing after 0s
Pending events from other users' wallets weren't visible because
getEvents() only returns events scoped to the admin's wallets.
Add separate getPendingEvents() that calls /events/pending endpoint.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 11:16:29 +02:00
d740cb1f97 fix: close self-closing q-badge tag in status column
Some checks failed
lint.yml / fix: close self-closing q-badge tag in status column (pull_request) Failing after 0s
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 11:11:13 +02:00
3425097a5c fix: close remaining self-closing q-btn tags in pending approvals
Some checks failed
lint.yml / fix: close remaining self-closing q-btn tags in pending approvals (pull_request) Failing after 0s
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 11:09:39 +02:00
cdfcee39ae fix: use explicit closing tags for Vue custom elements
Some checks failed
lint.yml / fix: use explicit closing tags for Vue custom elements (pull_request) Failing after 0s
Self-closing tags on custom elements (q-icon, q-badge) cause
Vue compiler-30 (missing end tag) errors in HTML-parsed templates.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 10:48:02 +02:00
bdd49f8612 fix: use v-text bindings instead of raw template tags in pending UI
Some checks failed
lint.yml / fix: use v-text bindings instead of raw template tags in pending UI (pull_request) Failing after 0s
Avoids Jinja/Vue template delimiter conflicts that cause Vue
compiler-30 errors (missing end tag from unescaped > in expressions).

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 10:41:41 +02:00
702ab70559 feat: add pending approvals UI to admin panel
Some checks failed
lint.yml / feat: add pending approvals UI to admin panel (pull_request) Failing after 0s
- Separate "Pending Approvals" card with approve/reject buttons
  (appears only when proposed events exist)
- Status badge column in events table (green/orange/red)
- Inline approve/reject buttons on proposed events in table
- Following castle extension's approval UI pattern

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 10:37:48 +02:00
32ea79a137 fix: make wallet optional in CreateEvent for propose endpoint
Some checks failed
lint.yml / fix: make wallet optional in CreateEvent for propose endpoint (pull_request) Failing after 0s
The propose endpoint sets wallet from the authenticated user's
invoice key. Making wallet optional in the model allows the
request body to omit it. The admin create endpoint falls back
to the auth wallet if not provided.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 10:32:16 +02:00
41e64adfde fix: resolve lint errors in views_api.py
Some checks failed
lint.yml / fix: resolve lint errors in views_api.py (pull_request) Failing after 0s
- Remove unused purge_unpaid_tickets import (add TODO comment)
- Break long line in ticket GET endpoint signature

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 09:08:23 +02:00
eb474b1390 fix: make promo_code and refund_address optional query params
Some checks failed
lint.yml / fix: make promo_code and refund_address optional query params (pull_request) Failing after 0s
These were required query params on the GET ticket endpoint,
causing 400 errors when not provided.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 09:04:46 +02:00
a41348df94 feat: add event proposal and approval API endpoints
- POST /api/v1/events/propose — submit event for approval (invoice key)
- GET /api/v1/events/pending — list proposed events (admin key)
- PUT /api/v1/events/{id}/approve — approve proposed event (admin key)
- PUT /api/v1/events/{id}/reject — reject proposed event (admin key)
- GET /api/v1/events/public — now returns only approved, non-canceled events

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 09:04:25 +02:00
0c782e6239 feat: add CRUD functions for public and pending event queries
- get_public_events(): returns approved, non-canceled events
- get_pending_events(): returns proposed events for admin review

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 09:02:18 +02:00
1dcff37df5 feat: add status field to Event model for approval workflow
Add 'status' column (proposed/approved/rejected) to the events
table with default 'approved' for backward compatibility. Existing
events are unaffected.

Migration m008 adds the column.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 09:01:50 +02:00
68e6e3d02e fix: Parse JSON extra field when reading tickets from database
Some checks failed
lint / lint (push) Has been cancelled
/ release (push) Has been cancelled
/ pullrequest (push) Has been cancelled
v0.0.2
The previous fix used db.insert() which serializes the extra field to JSON.
However, the read functions (get_ticket, get_tickets, etc.) use fetchone/fetchall
without a model parameter, so the extra field comes back as a JSON string.

Added _parse_ticket_row() helper that:
- Converts empty strings to None for name/email (existing logic)
- Parses extra field from JSON string if needed (new)

The isinstance(extra, str) check ensures compatibility with both:
- SQLite: returns JSON as string
- PostgreSQL/CockroachDB: may return native JSONB as dict

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-01-03 18:03:34 +01:00
a77145e08e fix: Use db.insert() for ticket creation to fix SQLite serialization
Some checks failed
lint / lint (push) Waiting to run
lint / lint (pull_request) Has been cancelled
The previous implementation used db.execute() with a raw dict, which
failed on SQLite because the 'extra' field (TicketExtra model) was
passed as a Python dict that SQLite cannot serialize.

Using db.insert() with the Pydantic model ensures proper JSON
serialization of the extra field across all database backends
(SQLite, PostgreSQL, CockroachDB).

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-01-03 17:48:46 +01:00
c49abdb53f Fix SQLite migration syntax error in m007
Some checks failed
lint / lint (push) Has been cancelled
/ release (push) Has been cancelled
/ pullrequest (push) Has been cancelled
v0.0.1
SQLite doesn't support adding multiple columns in a single ALTER TABLE
statement. Split into separate statements for each column.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2025-12-31 17:07:34 +01:00
4fb6d90fcd Adds public events endpoint and user tickets
Some checks are pending
lint / lint (push) Waiting to run
/ release (push) Waiting to run
/ pullrequest (push) Blocked by required conditions
Adds a public events endpoint that allows read-only access to all events.
Improves ticket management by adding support for user IDs as an identifier, alongside name and email.
This simplifies ticket creation for authenticated users and enhances security.
Also introduces an API endpoint to fetch tickets by user ID.
2025-12-31 12:54:12 +01:00
Tiago Vasconcelos
a9ac6dcfc1 feat: add promo codes and conditional events (#40)
* add extra column
* add conditional events
* refunds
* conditional events working
* adding promo codes
* promo codes logic

---------

Co-authored-by: dni  <office@dnilabs.com>
2025-12-31 12:52:32 +01:00
arbadacarba
44f2cb5a62 Fix typos (#39) 2025-12-31 12:49:29 +01:00
33977c53d6 Imports Optional type hint
Imports the `Optional` type hint from the `typing` module into `crud.py` and `models.py`.

This provides more explicit type annotations where values can be `None`.
2025-11-04 01:42:14 +01:00
7cc622fc44 Merge remote-tracking branch 'upstream/main' 2025-11-03 23:13:22 +01:00
c669da5822 Adds public events endpoint and user tickets
Adds a public events endpoint that allows read-only access to all events.
Improves ticket management by adding support for user IDs as an identifier, alongside name and email.
This simplifies ticket creation for authenticated users and enhances security.
Also introduces an API endpoint to fetch tickets by user ID.
2025-11-03 23:05:31 +01:00
Tiago Vasconcelos
ae827a6545
fix: QR copy button (#38)
Some checks failed
/ release (push) Has been cancelled
/ pullrequest (push) Has been cancelled
v1.1.0
* fix QR copy button
* fixup poetry
* rc6 and chore update

---------

Co-authored-by: dni  <office@dnilabs.com>
2025-09-04 07:10:49 +02:00
Tiago Vasconcelos
7aeba1eeb4
Update to use uv (#37)
---------

Co-authored-by: dni  <office@dnilabs.com>
2025-08-22 16:54:51 +02:00
dni ⚡
c729ef17a6
fix: 1.0.0-rc5
Some checks failed
/ release (push) Has been cancelled
/ pullrequest (push) Has been cancelled
v1.0.0
2024-10-22 10:49:52 +02:00
dni ⚡
6714dcddc7
feat: update to lnbits 1.0.0 (#36) 2024-10-11 13:52:39 +02:00
dni ⚡
9ca714d878
fix: fetch incoming payment (#35)
did not work for internal payment
2024-09-03 16:35:42 +02:00
dni ⚡
400b39211d
feat: code quality (#34)
* feat: code quality
2024-08-29 12:18:49 +02:00
Arc
3df2a56ca2
Merge pull request #30 from lnbits/advanceddescription
added video
2024-05-17 17:39:51 +01:00
benarc
ea3a60ecd4 Added video 2024-05-17 17:39:11 +01:00
benarc
57f40b9790 Merge remote-tracking branch 'origin/main' into advanceddescription 2024-05-17 17:38:28 +01:00
Vlad Stan
9c82d9e2df chore: bump min_lnbits_version
Some checks failed
/ release (push) Has been cancelled
/ pullrequest (push) Has been cancelled
v0.2.0
2024-05-14 11:37:27 +03:00
Arc
c24f5ddb84
Merge pull request #29 from lnbits/advanceddescription
Added extended description
2024-05-06 12:42:45 +01:00
Tiago Vasconcelos
082f5e7488
Check payment (#28)
Hotfix the check payment when using fiat tickets
2024-05-06 12:41:35 +01:00