Replaces the fragile NIP-55 intent/callback round-trip with the same
mechanism the desktop login uses: openNostrLogin signs the session
challenge via window.nostr — provided by an extension or by
window.nostr.js over a persistent NIP-46 connection (Amber pairing with
permissions). The listener stores a LoginKey for the page's k1 and
navigates to the completion route, which issues the token and redirects
into the app via the verified App Link handoff.
Amber drops the query string when it rebuilds the callback URL and
appends the signed event directly to the path. The mobile login page now
hands out path-based callback URLs (/auth/mobile/signed/{k1}/) so the
event arrives as the remainder of the path.
The new callback runs in the web middleware group: the signer opens it
in the system browser, which shares cookies with the in-app browser
session, so the flow completes immediately — a bridge page issues the
token and fires the einundzwanzig:// deep link. The LoginKey row is
still written as a fallback for the polling login page.
The Einundzwanzig mobile app opens /auth/mobile in an in-app browser.
After a Lightning (LNURL) or Nostr login the flow issues a personal
access token and hands it back via the einundzwanzig://auth deep link.
- New auth.mobile-login Livewire view: Lightning QR (shared k1) plus
Nostr signing via NIP-55 Android signers (Amber) with server callback,
and a confirmation screen for already authenticated sessions
- MobileAuthController: NIP-55 callback verification, completion route
issuing the token (replacing same-device tokens), redirect whitelist
- Nostr login event verification and npub user resolution extracted to
App\Support\NostrLogin, now shared with the interactive login
- GET /api/user (auth:sanctum) returns the token owner's profile
- Updated `authorizeAccess` to restrict `meetups.edit` views and updates to users in "My-Meetups".
- Attached creators to `meetup_user` pivot for default membership.
- Adjusted related tests to validate membership-based edit permissions.
📱 **Improve sidebar and mobile navigation accessibility**
- Added `aria-labels` to improve screen reader support for sidebar and mobile header elements.
- Updated desktop and mobile user menus alignment for consistency.
⚡ **Enhance Lightning login flow**
- Introduced `lightningLoginInProgress` for smoother polling synchronization with the redirect flow.
- Updated logic to dispatch `lightning-login-ready` event instead of immediate redirect, avoiding race conditions.
- 🔄 Added `x-effect` to lock page scrolling during login progress.
- 🛡️ Disabled login button and added loading indicators when `nostrLoginInProgress`.
- 🖼️ Introduced full-viewport progress overlay with accessible attributes and transitions.
- 🌐 Updated translations for signing states and instructions.
- 🛡️ Added `nostrLoginInProgress` flag to pause `wire:poll` during Nostr login round-trip.
- 🔄 Removed redundant `Session::regenerate()` to avoid session ID conflicts.
- 🪲 Improved error handling for signature serialization and Nostr signer unavailability.
- 🛡️ Avoided redundant `Session::regenerate` call as `Auth::loginUsingId` already updates the session ID.
- 🚀 Replaced `wire:navigate` with a full-page redirect to ensure a fresh CSRF token for Livewire actions.
- 🔄 `requestNostrChallenge` now issues a new challenge when needed.
- 🛡️ Enhanced fallback logic in `nostrLogin.js` to ensure robust challenge retrieval.
- ✅ Added test coverage for fresh challenge issuance.
- Remove unauthenticated /test route that dispatched FetchNostrProfileJob
for a hardcoded user (routes/web.php).
- Enforce created_by ownership check in meetup and lecturer Livewire edit
components; mirror the existing services/edit pattern.
- Replace blind-trust nostrLoggedIn handler with NIP-42-style signed event
verification: server-issued challenge stored in session, client signs a
kind:22242 event, server verifies signature via swentel/nostr-php and
derives npub. Challenge is single-use with 5-minute TTL.
- Validate the ?my[] parameter on the calendar download endpoint as an
array of integers and intersect with the authenticated user's meetups.
- Replaced `state` and `computed` with `Livewire\Component` implementations in `language/selector.blade.php` for enhanced maintainability.
- Adjusted `login.blade.php` syntax for dynamic href generation and removed commented-out sign-up link.
- Added unique `wire:key` attributes to iterable elements for enhanced performance and reactivity.
- Simplified controller routing and corrected indentation in `web.php`, improving clarity.
- Added `LnurlAuthController` to handle LNURL authentication flow with signature verification, user creation, and session expiry checks.
- Integrated authentication error polling in `nostrLogin.js`.
- Added `LoginKeyFactory` for testing and database seed purposes.
- Created feature tests (`LnurlAuthTest`) to validate LNURL callback, error responses, and session handling.
- Extended `login.blade.php` with dynamic error handling and reset logic for expired sessions.
- Introduced `livewire/livewire` v4 dependency.
- Added `config/livewire.php` for Livewire customization.
- Adjusted `login.blade.php` language fallback logic for session handling.
- Created new Blade layouts (`error.blade.php`, `auth.blade.php`, `app.blade.php`) for unified component architecture.
- Added a new `lang/pl.json` file with comprehensive Polish translations.
- Enhanced `lang/es.json` with additional Spanish keys and phrases for better coverage.
- Introduced `FetchNostrProfileJob` for retrieving and updating user Nostr profiles.
- Added Hungarian translations (`auth.php`, `passwords.php`, `validation.php`, and others) for improved localization.
- Integrated Laravel Horizon for enhanced queue management (`HorizonServiceProvider` added, `composer.json` updated).
- Updated German and Spanish language files to fix duplicate keys.
- Minor route addition for testing Nostr profile job dispatch.
- Implemented automatic creation of fallback users with default properties during login if no existing user is found.
- Standardized the redirect logic for the dashboard route with consistent parameter handling.
- Improved readability of route definitions by formatting parameters across multiple lines.
- Added `DomainMiddleware` to dynamically set locale, language-country session, and app name based on domain.
- Updated views and components to leverage `lang_country` session for language and region-specific content.
- Enhanced country parameter retrieval with `config('app.domain_country')` as fallback.
- Refined language filtering by scanning available language files dynamically.
- Added language-specific assets and translations (`nl.json`, `es.json`) with improved language-region associations.
- Updated `app-logo-icon` to display region-specific images or default SVGs.
- Improved views with cleaner, dynamic rendering and session-aware functionalities.
- Added `#[SeoDataAttribute]` annotations to Livewire components for SEO management.
- Extended translations in English, Spanish, and German for better localization support.
- Introduced `config/seo.php` to centralize SEO settings.
- Implemented `SeoTrait` for dynamic SEO management.
- Added `SeoDataAttribute` to set SEO metadata at the class level.
- Updated various views to integrate dynamic SEO handling.
- Included fallback settings for titles, descriptions, images, and more.
- Added `publicDisk` configuration to `filesystems.php`.
- Expanded locale translations in `es.json` and `de.json`.
- Implemented RSS, Atom, and JSON feed views.
- Added `feed.php` configuration for feed generation.
- Introduced `ImageController` for image handling.
- Updated application routing to include `api.php`.
- 🔒 Introduced Nostr-based login functionality with `nostr-tools` integration.
- 🖼️ Added user profile photo handling (upload, delete, and URL retrieval) in the `User` model.
- 💻 Updated views to use `flux:avatar` for consistent user avatars.
- ✂️ Removed unused routes and adjusted dashboard routing logic.
- 📦 Updated dependencies in `package.json` and `yarn.lock`.