'handleNostrLoggedIn', 'nostrLoggedOut' => 'handleNostrLoggedOut', ]; public function mount(): void { if (NostrAuth::check()) { $this->currentPubkey = NostrAuth::pubkey(); $this->currentPleb = EinundzwanzigPleb::query() ->with([ 'paymentEvents' => fn ($query) => $query->where('year', date('Y')), ]) ->where('pubkey', $this->currentPubkey)->first(); if ($this->currentPleb) { $this->email = $this->currentPleb->email; $this->showEmail = ! $this->no; if ($this->currentPleb->association_status === AssociationStatus::ACTIVE) { $this->amountToPay = config('app.env') === 'production' ? 21000 : 1; } if ($this->currentPleb->paymentEvents->count() < 1) { $this->createPaymentEvent(); $this->currentPleb->load('paymentEvents'); } $this->loadEvents(); $this->listenForPayment(); } } } public function handleNostrLoggedIn($pubkey): void { NostrAuth::login($pubkey); $this->currentPubkey = $pubkey; $this->currentPleb = EinundzwanzigPleb::query() ->with([ 'paymentEvents' => fn ($query) => $query->where('year', date('Y')), ]) ->where('pubkey', $pubkey)->first(); $this->email = $this->currentPleb->email; $this->no = $this->currentPleb->no_email; $this->showEmail = ! $this->no; if ($this->currentPleb->association_status === AssociationStatus::ACTIVE) { $this->amountToPay = config('app.env') === 'production' ? 21000 : 1; } if ($this->currentPleb->paymentEvents->count() < 1) { $this->createPaymentEvent(); $this->currentPleb->load('paymentEvents'); } $this->loadEvents(); $this->listenForPayment(); } public function handleNostrLoggedOut(): void { NostrAuth::logout(); $this->currentPubkey = null; $this->currentPleb = null; $this->yearsPaid = []; $this->events = []; $this->payments = []; $this->qrCode = null; $this->amountToPay = config('app.env') === 'production' ? 21000 : 1; $this->currentYearIsPaid = false; } public function updatedNo(): void { $this->showEmail = ! $this->no; $this->currentPleb->update([ 'no_email' => $this->no, ]); } public function updatedFax(): void { $this->js('alert("Markus Turm wird sich per Fax melden!")'); } public function saveEmail(): void { $this->validate([ 'email' => 'required|email', ]); $this->currentPleb->update([ 'email' => $this->email, ]); $notification = new Notification($this); $notification->success('E-Mail Adresse gespeichert.'); } public function pay($comment): \Illuminate\Http\RedirectResponse { $paymentEvent = $this->currentPleb ->paymentEvents() ->where('year', date('Y')) ->first(); if ($paymentEvent->btc_pay_invoice) { return redirect('https://pay.einundzwanzig.space/i/'.$paymentEvent->btc_pay_invoice); } try { $response = \Illuminate\Support\Facades\Http::withHeaders([ 'Authorization' => 'token '.config('services.btc_pay.api_key'), ])->post( 'https://pay.einundzwanzig.space/api/v1/stores/98PF86BoMd3C8P1nHHyFdoeznCwtcm5yehcAgoCYDQ2a/invoices', [ 'amount' => $this->amountToPay, 'metadata' => [ 'orderId' => $comment, 'orderUrl' => url()->route('association.profile'), 'itemDesc' => 'Mitgliedsbeitrag '.date('Y').' von nostr:'.$this->currentPleb->npub, 'posData' => [ 'event' => $paymentEvent->event_id, 'pubkey' => $this->currentPleb->pubkey, 'npub' => $this->currentPleb->npub, ], ], 'checkout' => [ 'expirationMinutes' => 60 * 24, 'redirectURL' => url()->route('association.profile'), 'redirectAutomatically' => true, 'defaultLanguage' => 'de', ], ], )->throw(); $paymentEvent->btc_pay_invoice = $response->json()['id']; $paymentEvent->save(); return redirect($response->json()['checkoutLink']); } catch (\Exception $e) { $notification = new Notification($this); $notification->error( 'Fehler beim Erstellen der Rechnung. Bitte versuche es später erneut: '.$e->getMessage(), ); return redirect()->route('association.profile'); } } public function listenForPayment(): void { $paymentEvent = $this->currentPleb ->paymentEvents() ->where('year', date('Y')) ->first(); if ($paymentEvent->btc_pay_invoice) { $response = \Illuminate\Support\Facades\Http::withHeaders([ 'Authorization' => 'token '.config('services.btc_pay.api_key'), ]) ->get( 'https://pay.einundzwanzig.space/api/v1/stores/98PF86BoMd3C8P1nHHyFdoeznCwtcm5yehcAgoCYDQ2a/invoices/'.$paymentEvent->btc_pay_invoice, ); if ($response->json()['status'] === 'Expired') { $paymentEvent->btc_pay_invoice = null; $paymentEvent->paid = false; $paymentEvent->save(); } if ($response->json()['status'] === 'Settled') { $paymentEvent->paid = true; $paymentEvent->save(); $this->currentYearIsPaid = true; } } if ($paymentEvent->paid) { $this->currentYearIsPaid = true; } $paymentEvent = $paymentEvent->refresh(); $this->payments = $this->currentPleb ->paymentEvents() ->where('paid', true) ->get(); } public function save($type): void { $this->form->validate(); if (! $this->form->check) { $this->js('alert("Du musst den Statuten zustimmen.")'); return; } $this->currentPleb ->update([ 'association_status' => $type, ]); } public function createPaymentEvent(): void { $note = new NostrEvent; $note->setKind(32121); $note->setContent( 'Dieses Event dient der Zahlung des Mitgliedsbeitrags für das Jahr '.date( 'Y', ).'. Bitte bezahle den Betrag von '.number_format($this->amountToPay, 0, ',', '.').' Satoshis.', ); $note->setTags([ ['d', $this->currentPleb->pubkey.','.date('Y')], ['zap', 'daf83d92768b5d0005373f83e30d4203c0b747c170449e02fea611a0da125ee6', config('services.relay'), '1'], ]); $signer = new Sign; $signer->signEvent($note, config('services.nostr')); $eventMessage = new EventMessage($note); $relayUrl = config('services.relay'); $relay = new Relay($relayUrl); $relay->setMessage($eventMessage); $result = $relay->send(); $this->currentPleb->paymentEvents()->create([ 'year' => date('Y'), 'event_id' => $result->eventId, 'amount' => $this->amountToPay, ]); } public function loadEvents(): void { $subscription = new Subscription; $subscriptionId = $subscription->setId(); $filter1 = new Filter; $filter1->setKinds([32121]); $filter1->setAuthors(['daf83d92768b5d0005373f83e30d4203c0b747c170449e02fea611a0da125ee6']); $filters = [$filter1]; $requestMessage = new RequestMessage($subscriptionId, $filters); $relays = [ new Relay(config('services.relay')), ]; $relaySet = new RelaySet; $relaySet->setRelays($relays); $request = new Request($relaySet, $requestMessage); $response = $request->send(); $this->events = collect($response[config('services.relay')]) ->map(function ($event) { if (! isset($event->event)) { return false; } return [ 'id' => $event->event->id, 'kind' => $event->event->kind, 'content' => $event->event->content, 'pubkey' => $event->event->pubkey, 'tags' => $event->event->tags, 'created_at' => $event->event->created_at, ]; }) ->filter() ->unique('id') ->toArray(); } } ?>