Compare commits
No commits in common. "266e9a892d0e4db59885a43c005ee874dff69308" and "5cfefc1ca84a95c434c4b441793f11652de8ef35" have entirely different histories.
266e9a892d
...
5cfefc1ca8
@ -23,7 +23,7 @@ export async function getCost ({ subName, parentId, uploadIds, boost = 0, bio },
|
||||
|
||||
// sub allows freebies (or is a bio or a comment), cost is less than baseCost, not anon,
|
||||
// cost must be greater than user's balance, and user has not disabled freebies
|
||||
const freebie = (parentId || bio) && cost <= baseCost && !!me &&
|
||||
const freebie = (parentId || bio || sub?.allowFreebies) && cost <= baseCost && !!me &&
|
||||
cost > me?.msats && !me?.disableFreebies
|
||||
|
||||
return freebie ? BigInt(0) : BigInt(cost)
|
||||
|
@ -23,19 +23,19 @@ import performPaidAction from '../paidAction'
|
||||
|
||||
function commentsOrderByClause (me, models, sort) {
|
||||
if (sort === 'recent') {
|
||||
return 'ORDER BY ("Item"."deletedAt" IS NULL) DESC, ("Item".cost > 0 OR "Item"."weightedVotes" - "Item"."weightedDownVotes" > 0) DESC, "Item".created_at DESC, "Item".id DESC'
|
||||
return 'ORDER BY "Item".created_at DESC, "Item".id DESC'
|
||||
}
|
||||
|
||||
if (me && sort === 'hot') {
|
||||
return `ORDER BY ("Item"."deletedAt" IS NULL) DESC, COALESCE(
|
||||
return `ORDER BY COALESCE(
|
||||
personal_hot_score,
|
||||
${orderByNumerator(models, 0)}/POWER(GREATEST(3, EXTRACT(EPOCH FROM (now_utc() - "Item".created_at))/3600), 1.3)) DESC NULLS LAST,
|
||||
"Item".msats DESC, ("Item".cost > 0) DESC, "Item".id DESC`
|
||||
} else {
|
||||
if (sort === 'top') {
|
||||
return `ORDER BY ("Item"."deletedAt" IS NULL) DESC, ${orderByNumerator(models, 0)} DESC NULLS LAST, "Item".msats DESC, ("Item".cost > 0) DESC, "Item".id DESC`
|
||||
return `ORDER BY ${orderByNumerator(models, 0)} DESC NULLS LAST, "Item".msats DESC, ("Item".cost > 0) DESC, "Item".id DESC`
|
||||
} else {
|
||||
return `ORDER BY ("Item"."deletedAt" IS NULL) DESC, ${orderByNumerator(models, 0)}/POWER(GREATEST(3, EXTRACT(EPOCH FROM (now_utc() - "Item".created_at))/3600), 1.3) DESC NULLS LAST, "Item".msats DESC, ("Item".cost > 0) DESC, "Item".id DESC`
|
||||
return `ORDER BY ${orderByNumerator(models, 0)}/POWER(GREATEST(3, EXTRACT(EPOCH FROM (now_utc() - "Item".created_at))/3600), 1.3) DESC NULLS LAST, "Item".msats DESC, ("Item".cost > 0) DESC, "Item".id DESC`
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1290,7 +1290,11 @@ export const updateItem = async (parent, { sub: subName, forward, ...item }, { m
|
||||
const differentSub = subName && old.subName !== subName
|
||||
if (differentSub) {
|
||||
const sub = await models.sub.findUnique({ where: { name: subName } })
|
||||
if (sub.baseCost > old.sub.baseCost) {
|
||||
if (old.cost === 0) {
|
||||
if (!sub.allowFreebies) {
|
||||
throw new GraphQLError(`~${subName} does not allow freebies`, { extensions: { code: 'BAD_INPUT' } })
|
||||
}
|
||||
} else if (sub.baseCost > old.sub.baseCost) {
|
||||
throw new GraphQLError('cannot change to a more expensive sub', { extensions: { code: 'BAD_INPUT' } })
|
||||
}
|
||||
}
|
||||
|
@ -16,7 +16,7 @@ export default gql`
|
||||
|
||||
extend type Mutation {
|
||||
upsertSub(oldName: String, name: String!, desc: String, baseCost: Int!,
|
||||
postTypes: [String!]!,
|
||||
postTypes: [String!]!, allowFreebies: Boolean!,
|
||||
billingType: String!, billingAutoRenew: Boolean!,
|
||||
moderated: Boolean!, nsfw: Boolean!): SubPaidAction!
|
||||
paySub(name: String!): SubPaidAction!
|
||||
@ -24,7 +24,7 @@ export default gql`
|
||||
toggleSubSubscription(name: String!): Boolean!
|
||||
transferTerritory(subName: String!, userName: String!): Sub
|
||||
unarchiveTerritory(name: String!, desc: String, baseCost: Int!,
|
||||
postTypes: [String!]!,
|
||||
postTypes: [String!]!, allowFreebies: Boolean!,
|
||||
billingType: String!, billingAutoRenew: Boolean!,
|
||||
moderated: Boolean!, nsfw: Boolean!): SubPaidAction!
|
||||
}
|
||||
|
@ -14,7 +14,7 @@ import { SubmitButton } from './form'
|
||||
|
||||
const FeeButtonContext = createContext()
|
||||
|
||||
export function postCommentBaseLineItems ({ baseCost = 1, comment = false, me }) {
|
||||
export function postCommentBaseLineItems ({ baseCost = 1, comment = false, allowFreebies = true, me }) {
|
||||
const anonCharge = me
|
||||
? {}
|
||||
: {
|
||||
@ -29,7 +29,7 @@ export function postCommentBaseLineItems ({ baseCost = 1, comment = false, me })
|
||||
term: baseCost,
|
||||
label: `${comment ? 'comment' : 'post'} cost`,
|
||||
modifier: (cost) => cost + baseCost,
|
||||
allowFreebies: comment
|
||||
allowFreebies
|
||||
},
|
||||
...anonCharge
|
||||
}
|
||||
|
@ -149,7 +149,7 @@ export function PostForm ({ type, sub, children }) {
|
||||
|
||||
return (
|
||||
<FeeButtonProvider
|
||||
baseLineItems={sub ? postCommentBaseLineItems({ baseCost: sub.baseCost, me: !!me }) : undefined}
|
||||
baseLineItems={sub ? postCommentBaseLineItems({ baseCost: sub.baseCost, allowFreebies: sub.allowFreebies, me: !!me }) : undefined}
|
||||
useRemoteLineItems={postCommentUseRemoteLineItems({ me: !!me })}
|
||||
>
|
||||
<FormType sub={sub}>{children}</FormType>
|
||||
|
@ -91,6 +91,7 @@ export default function TerritoryForm ({ sub }) {
|
||||
desc: sub?.desc || '',
|
||||
baseCost: sub?.baseCost || 10,
|
||||
postTypes: sub?.postTypes || POST_TYPES,
|
||||
allowFreebies: typeof sub?.allowFreebies === 'undefined' ? true : sub?.allowFreebies,
|
||||
billingType: sub?.billingType || 'MONTHLY',
|
||||
billingAutoRenew: sub?.billingAutoRenew || false,
|
||||
moderated: sub?.moderated || false,
|
||||
@ -132,9 +133,15 @@ export default function TerritoryForm ({ sub }) {
|
||||
label='post cost'
|
||||
name='baseCost'
|
||||
type='number'
|
||||
groupClassName='mb-2'
|
||||
required
|
||||
append={<InputGroup.Text className='text-monospace'>sats</InputGroup.Text>}
|
||||
/>
|
||||
<Checkbox
|
||||
label='allow free posts'
|
||||
name='allowFreebies'
|
||||
groupClassName='ms-1'
|
||||
/>
|
||||
<CheckboxGroup label='post types' name='postTypes'>
|
||||
<Row>
|
||||
<Col xs={4} sm='auto'>
|
||||
|
@ -223,10 +223,10 @@ export const UPDATE_COMMENT = gql`
|
||||
export const UPSERT_SUB = gql`
|
||||
${PAID_ACTION}
|
||||
mutation upsertSub($oldName: String, $name: String!, $desc: String, $baseCost: Int!,
|
||||
$postTypes: [String!]!, $billingType: String!,
|
||||
$postTypes: [String!]!, $allowFreebies: Boolean!, $billingType: String!,
|
||||
$billingAutoRenew: Boolean!, $moderated: Boolean!, $nsfw: Boolean!) {
|
||||
upsertSub(oldName: $oldName, name: $name, desc: $desc, baseCost: $baseCost,
|
||||
postTypes: $postTypes, billingType: $billingType,
|
||||
postTypes: $postTypes, allowFreebies: $allowFreebies, billingType: $billingType,
|
||||
billingAutoRenew: $billingAutoRenew, moderated: $moderated, nsfw: $nsfw) {
|
||||
result {
|
||||
name
|
||||
@ -238,10 +238,10 @@ export const UPSERT_SUB = gql`
|
||||
export const UNARCHIVE_TERRITORY = gql`
|
||||
${PAID_ACTION}
|
||||
mutation unarchiveTerritory($name: String!, $desc: String, $baseCost: Int!,
|
||||
$postTypes: [String!]!, $billingType: String!,
|
||||
$postTypes: [String!]!, $allowFreebies: Boolean!, $billingType: String!,
|
||||
$billingAutoRenew: Boolean!, $moderated: Boolean!, $nsfw: Boolean!) {
|
||||
unarchiveTerritory(name: $name, desc: $desc, baseCost: $baseCost,
|
||||
postTypes: $postTypes, billingType: $billingType,
|
||||
postTypes: $postTypes, allowFreebies: $allowFreebies, billingType: $billingType,
|
||||
billingAutoRenew: $billingAutoRenew, moderated: $moderated, nsfw: $nsfw) {
|
||||
result {
|
||||
name
|
||||
|
@ -7,6 +7,7 @@ export const SUB_FIELDS = gql`
|
||||
name
|
||||
createdAt
|
||||
postTypes
|
||||
allowFreebies
|
||||
rankingType
|
||||
billingType
|
||||
billingCost
|
||||
|
@ -137,10 +137,6 @@ export const WALLET = gql`
|
||||
... on WalletNwc {
|
||||
nwcUrlRecv
|
||||
}
|
||||
... on WalletPhoenixd {
|
||||
url
|
||||
secondaryPassword
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -177,10 +173,6 @@ export const WALLET_BY_TYPE = gql`
|
||||
... on WalletNwc {
|
||||
nwcUrlRecv
|
||||
}
|
||||
... on WalletPhoenixd {
|
||||
url
|
||||
secondaryPassword
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -762,26 +762,6 @@ export const lncSchema = object({
|
||||
.required('required')
|
||||
})
|
||||
|
||||
export const phoenixdSchema = object().shape({
|
||||
url: string().url().required('required').trim(),
|
||||
primaryPassword: string().length(64).hex()
|
||||
.when(['secondaryPassword'], ([secondary], schema) => {
|
||||
if (!secondary) return schema.required('required if secondary password not set')
|
||||
return schema.test({
|
||||
test: primary => secondary !== primary,
|
||||
message: 'primary password cannot be the same as secondary password'
|
||||
})
|
||||
}),
|
||||
secondaryPassword: string().length(64).hex()
|
||||
.when(['primaryPassword'], ([primary], schema) => {
|
||||
if (!primary) return schema.required('required if primary password not set')
|
||||
return schema.test({
|
||||
test: secondary => primary !== secondary,
|
||||
message: 'secondary password cannot be the same as primary password'
|
||||
})
|
||||
})
|
||||
}, ['primaryPassword', 'secondaryPassword'])
|
||||
|
||||
export const bioSchema = object({
|
||||
bio: string().required('required').trim()
|
||||
})
|
||||
|
@ -257,9 +257,9 @@ export default function Settings ({ ssrData }) {
|
||||
label={
|
||||
<div className='d-flex align-items-center'>disable freebies
|
||||
<Info>
|
||||
<p>Some comments can be created without paying. However, those comments have limited visibility.</p>
|
||||
<p>Some posts and comments can be created without paying. However, that content has limited visibility.</p>
|
||||
|
||||
<p>If you disable freebies, you will always pay for your comments and get standard visibility.</p>
|
||||
<p>If you disable freebies, you will always pay for your posts and comments and get standard visibility.</p>
|
||||
|
||||
<p>If you attach a sending wallet, we disable freebies for you unless you have checked/unchecked this value already.</p>
|
||||
</Info>
|
||||
|
@ -1,24 +0,0 @@
|
||||
-- AlterEnum
|
||||
ALTER TYPE "WalletType" ADD VALUE 'PHOENIXD';
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "WalletPhoenixd" (
|
||||
"id" SERIAL NOT NULL,
|
||||
"walletId" INTEGER NOT NULL,
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"url" TEXT NOT NULL,
|
||||
"secondaryPassword" TEXT NOT NULL,
|
||||
|
||||
CONSTRAINT "WalletPhoenixd_pkey" PRIMARY KEY ("id")
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "WalletPhoenixd_walletId_key" ON "WalletPhoenixd"("walletId");
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "WalletPhoenixd" ADD CONSTRAINT "WalletPhoenixd_walletId_fkey" FOREIGN KEY ("walletId") REFERENCES "Wallet"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
CREATE TRIGGER wallet_phoenixd_as_jsonb
|
||||
AFTER INSERT OR UPDATE ON "WalletPhoenixd"
|
||||
FOR EACH ROW EXECUTE PROCEDURE wallet_wallet_type_as_jsonb();
|
@ -171,7 +171,6 @@ enum WalletType {
|
||||
CLN
|
||||
LNBITS
|
||||
NWC
|
||||
PHOENIXD
|
||||
}
|
||||
|
||||
model Wallet {
|
||||
@ -197,7 +196,6 @@ model Wallet {
|
||||
walletCLN WalletCLN?
|
||||
walletLNbits WalletLNbits?
|
||||
walletNWC WalletNWC?
|
||||
walletPhoenixd WalletPhoenixd?
|
||||
withdrawals Withdrawl[]
|
||||
InvoiceForward InvoiceForward[]
|
||||
|
||||
@ -266,16 +264,6 @@ model WalletNWC {
|
||||
nwcUrlRecv String
|
||||
}
|
||||
|
||||
model WalletPhoenixd {
|
||||
id Int @id @default(autoincrement())
|
||||
walletId Int @unique
|
||||
wallet Wallet @relation(fields: [walletId], references: [id], onDelete: Cascade)
|
||||
createdAt DateTime @default(now()) @map("created_at")
|
||||
updatedAt DateTime @default(now()) @updatedAt @map("updated_at")
|
||||
url String
|
||||
secondaryPassword String
|
||||
}
|
||||
|
||||
model Mute {
|
||||
muterId Int
|
||||
mutedId Int
|
||||
|
@ -1,184 +0,0 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
cat <<EOF
|
||||
.__ .__ __
|
||||
____ ____ ______ _ _______ | | | | _____/ |_
|
||||
/ ___\_/ __ \ / \ \/ \/ /\__ \ | | | | _/ __ \ __\\
|
||||
/ /_/ > ___/| | \ / / __ \| |_| |_\ ___/| |
|
||||
\___ / \___ >___| /\/\_/ (____ /____/____/\___ >__|
|
||||
/_____/ \/ \/ \/ \/
|
||||
|
||||
EOF
|
||||
|
||||
error () {
|
||||
echo -n "error: $1"
|
||||
exit 1
|
||||
}
|
||||
|
||||
wallet=$1
|
||||
[ -z $wallet ] && read -p "Enter wallet name: " wallet
|
||||
[ -z $wallet ] && error "name required"
|
||||
|
||||
# default is wallet in UPPERCASE
|
||||
walletType="${wallet^^}"
|
||||
read -p "Enter walletType (default $walletType): " _walletType
|
||||
if [ ! -z $_walletType ]; then
|
||||
walletType=$_walletType
|
||||
fi
|
||||
|
||||
# default is wallet capitalized with "wallet" prefix
|
||||
walletField="wallet${wallet^}"
|
||||
read -p "Enter walletField (default $walletField): " _walletField
|
||||
if [ ! -z $_walletField ]; then
|
||||
walletField=$_walletField
|
||||
fi
|
||||
|
||||
# exit on first failed command
|
||||
set -e
|
||||
|
||||
todo() {
|
||||
echo "// $wallet::TODO"
|
||||
}
|
||||
|
||||
# create folder and index.js
|
||||
mkdir -p wallets/$wallet
|
||||
cat > wallets/$wallet/index.js <<EOF
|
||||
$(todo)
|
||||
// create validation schema for wallet and import here
|
||||
// import { ${wallet}Schema } from '@/lib/validate'
|
||||
|
||||
export const name = '$wallet'
|
||||
|
||||
$(todo)
|
||||
// configure wallet fields
|
||||
export const fields = []
|
||||
|
||||
$(todo)
|
||||
// configure wallet card
|
||||
export const card = {
|
||||
title: '$wallet',
|
||||
subtitle: '',
|
||||
badges: []
|
||||
}
|
||||
|
||||
$(todo)
|
||||
// set validation schema
|
||||
export const fieldValidation = null // ${wallet}Schema
|
||||
|
||||
export const walletType = '$walletType'
|
||||
|
||||
export const walletField = '$walletField'
|
||||
|
||||
EOF
|
||||
|
||||
# create client.js
|
||||
cat > wallets/$wallet/client.js <<EOF
|
||||
export * from 'wallets/$wallet'
|
||||
|
||||
export async function testSendPayment (config, { logger }) {
|
||||
$(todo)
|
||||
}
|
||||
|
||||
export async function sendPayment (bolt11, config) {
|
||||
$(todo)
|
||||
}
|
||||
|
||||
EOF
|
||||
|
||||
# create server.js
|
||||
cat > wallets/$wallet/server.js <<EOF
|
||||
export * from 'wallets/$wallet'
|
||||
|
||||
export async function testCreateInvoice (config) {
|
||||
$(todo)
|
||||
}
|
||||
|
||||
export async function createInvoice (
|
||||
{ msats, description, descriptionHash, expiry },
|
||||
config
|
||||
) {
|
||||
$(todo)
|
||||
}
|
||||
|
||||
EOF
|
||||
|
||||
# add TODOs where manual update is needed
|
||||
fragments=fragments/wallet.js
|
||||
i=0
|
||||
grep -n "// XXX \[WALLET\]" $fragments | while read -r match;
|
||||
do
|
||||
lineno=$(echo $match | cut -d':' -f1)
|
||||
sed -i "$((lineno+i))i $(todo)" $fragments
|
||||
i=$((i+1))
|
||||
done
|
||||
|
||||
client=wallets/client.js
|
||||
lineno=$(grep -n "export default" $client | cut -d':' -f1)
|
||||
sed -i "${lineno}i $(todo)" $client
|
||||
|
||||
server=wallets/server.js
|
||||
lineno=$(grep -n "export default" $server | cut -d':' -f1)
|
||||
sed -i "${lineno}i $(todo)" $server
|
||||
|
||||
# need to disable exit on failure since we run grep to check its exit code
|
||||
set +e
|
||||
|
||||
# check if prisma/schema.prisma needs patch
|
||||
schema=prisma/schema.prisma
|
||||
grep --quiet "$walletField" $schema
|
||||
if [ $? -eq 1 ]; then
|
||||
tablename=${walletField^}
|
||||
# find line to insert walletField in wallet model
|
||||
lineno=$(grep -n "model Wallet {" $schema | cut -d':' -f1)
|
||||
offset=$(tail -n +$lineno $schema | grep -nm 1 "}" | cut -d':' -f1)
|
||||
offset=$(tail -n +$lineno $schema | head -n $offset | grep -nE "wallet[[:alpha:]]+\s+ Wallet[[:alpha:]]" | cut -d':' -f1 | tail -n1)
|
||||
sed -i "$((lineno+offset))i\ \ $walletField $tablename?" $schema
|
||||
|
||||
# find line to insert model for wallet
|
||||
lineno=$(grep -nE "model Wallet[[:alpha:]]+ {" $schema | cut -d':' -f1 | tail -n1)
|
||||
offset=$(tail -n +$((lineno+1)) $schema | grep -nm 1 "{" | cut -d':' -f1)
|
||||
i=$((lineno+offset))
|
||||
sed -i "${i}i $(todo)" $schema
|
||||
sed -i "$((i+1))i model Wallet${wallet^} {\n" $schema
|
||||
sed -i "$((i+2))i\ \ id Int @id @default(autoincrement())" $schema
|
||||
sed -i "$((i+3))i\ \ walletId Int @unique" $schema
|
||||
sed -i "$((i+4))i\ \ wallet Wallet @relation(fields: [walletId], references: [id], onDelete: Cascade)" $schema
|
||||
sed -i "$((i+5))i\ \ createdAt DateTime @default(now()) @map(\"created_at\")" $schema
|
||||
sed -i "$((i+6))i\ \ updatedAt DateTime @default(now()) @updatedAt @map(\"updated_at\")" $schema
|
||||
sed -i "$((i+7))i }" $schema
|
||||
|
||||
# find line to insert wallet type
|
||||
lineno=$(grep -nE "enum WalletType {" $schema | cut -d':' -f1)
|
||||
offset=$(tail -n +$lineno $schema | grep -nm 1 "}" | cut -d':' -f1)
|
||||
i=$((lineno+offset-1))
|
||||
sed -i "${i} i\ \ ${walletType}" $schema
|
||||
|
||||
# create migration file with TODOs
|
||||
migrationDir="prisma/migrations/$(date +%Y%m%d%H%M%S_$wallet)"
|
||||
mkdir -p $migrationDir
|
||||
cat > $migrationDir/migration.sql <<EOF
|
||||
-- AlterEnum
|
||||
ALTER TYPE "WalletType" ADD VALUE '${walletType}';
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "$tablename" (
|
||||
"id" SERIAL NOT NULL,
|
||||
"walletId" INTEGER NOT NULL,
|
||||
"created_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
"updated_at" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
||||
-- $wallet::TODO
|
||||
|
||||
CONSTRAINT "${tablename}_pkey" PRIMARY KEY ("int")
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "${tablename}_walletId_key" ON "$tablename"("walletId");
|
||||
|
||||
-- AddForeignKey
|
||||
ALTER TABLE "$tablename" ADD CONSTRAINT "${tablename}_walletId_fkey" FOREIGN KEY ("walletId") REFERENCES "Wallet"("id") ON DELETE CASCADE ON UPDATE CASCADE;
|
||||
|
||||
CREATE TRIGGER wallet_${wallet}_as_jsonb
|
||||
AFTER INSERT OR UPDATE ON "$tablename"
|
||||
FOR EACH ROW EXECUTE PROCEDURE wallet_wallet_type_as_jsonb();
|
||||
EOF
|
||||
fi
|
@ -6,6 +6,5 @@ import * as cln from 'wallets/cln/client'
|
||||
import * as lnd from 'wallets/lnd/client'
|
||||
import * as webln from 'wallets/webln/client'
|
||||
import * as blink from 'wallets/blink/client'
|
||||
import * as phoenixd from 'wallets/phoenixd/client'
|
||||
|
||||
export default [nwc, lnbits, lnc, lnAddr, cln, lnd, webln, blink, phoenixd]
|
||||
export default [nwc, lnbits, lnc, lnAddr, cln, lnd, webln, blink]
|
||||
|
@ -1,39 +0,0 @@
|
||||
export * from 'wallets/phoenixd'
|
||||
|
||||
export async function testSendPayment (config, { logger }) {
|
||||
// TODO:
|
||||
// Not sure which endpoint to call to test primary password
|
||||
// see https://phoenix.acinq.co/server/api
|
||||
// Maybe just wait until test payments with HODL invoices?
|
||||
|
||||
}
|
||||
|
||||
export async function sendPayment (bolt11, { url, primaryPassword }) {
|
||||
// https://phoenix.acinq.co/server/api#pay-bolt11-invoice
|
||||
const path = '/payinvoice'
|
||||
|
||||
const headers = new Headers()
|
||||
headers.set('Authorization', 'Basic ' + Buffer.from(':' + primaryPassword).toString('base64'))
|
||||
headers.set('Content-type', 'application/x-www-form-urlencoded')
|
||||
|
||||
const body = new URLSearchParams()
|
||||
body.append('invoice', bolt11)
|
||||
|
||||
const res = await fetch(url + path, {
|
||||
method: 'POST',
|
||||
headers,
|
||||
body
|
||||
})
|
||||
if (!res.ok) {
|
||||
const error = await res.text()
|
||||
throw new Error(error)
|
||||
}
|
||||
|
||||
const payment = await res.json()
|
||||
const preimage = payment.paymentPreimage
|
||||
if (!preimage) {
|
||||
throw new Error(payment.reason)
|
||||
}
|
||||
|
||||
return payment.paymentPreimage
|
||||
}
|
@ -1,45 +0,0 @@
|
||||
import { phoenixdSchema } from '@/lib/validate'
|
||||
|
||||
export const name = 'phoenixd'
|
||||
|
||||
// configure wallet fields
|
||||
export const fields = [
|
||||
{
|
||||
name: 'url',
|
||||
label: 'url',
|
||||
type: 'text'
|
||||
},
|
||||
{
|
||||
name: 'primaryPassword',
|
||||
label: 'primary password',
|
||||
type: 'password',
|
||||
optional: 'for sending',
|
||||
help: 'You can find the primary password as `http-password` in your phoenixd configuration file as mentioned [here](https://phoenix.acinq.co/server/api#security).',
|
||||
clientOnly: true,
|
||||
editable: false
|
||||
},
|
||||
{
|
||||
name: 'secondaryPassword',
|
||||
label: 'secondary password',
|
||||
type: 'password',
|
||||
optional: 'for receiving',
|
||||
help: 'You can find the secondary password as `http-password-limited-access` in your phoenixd configuration file as mentioned [here](https://phoenix.acinq.co/server/api#security).',
|
||||
serverOnly: true,
|
||||
editable: false
|
||||
}
|
||||
]
|
||||
|
||||
// configure wallet card
|
||||
export const card = {
|
||||
title: 'phoenixd',
|
||||
subtitle: 'use [phoenixd](https://phoenix.acinq.co/server) for payments',
|
||||
badges: ['send & receive']
|
||||
}
|
||||
|
||||
// phoenixd::TODO
|
||||
// set validation schema
|
||||
export const fieldValidation = phoenixdSchema
|
||||
|
||||
export const walletType = 'PHOENIXD'
|
||||
|
||||
export const walletField = 'walletPhoenixd'
|
@ -1,38 +0,0 @@
|
||||
import { msatsToSats } from '@/lib/format'
|
||||
|
||||
export * from 'wallets/phoenixd'
|
||||
|
||||
export async function testCreateInvoice ({ url, secondaryPassword }) {
|
||||
return await createInvoice(
|
||||
{ msats: 1000, description: 'SN test invoice', expiry: 1 },
|
||||
{ url, secondaryPassword })
|
||||
}
|
||||
|
||||
export async function createInvoice (
|
||||
{ msats, description, descriptionHash, expiry },
|
||||
{ url, secondaryPassword }
|
||||
) {
|
||||
// https://phoenix.acinq.co/server/api#create-bolt11-invoice
|
||||
const path = '/createinvoice'
|
||||
|
||||
const headers = new Headers()
|
||||
headers.set('Authorization', 'Basic ' + Buffer.from(':' + secondaryPassword).toString('base64'))
|
||||
headers.set('Content-type', 'application/x-www-form-urlencoded')
|
||||
|
||||
const body = new URLSearchParams()
|
||||
body.append('description', description)
|
||||
body.append('amountSat', msatsToSats(msats))
|
||||
|
||||
const res = await fetch(url + path, {
|
||||
method: 'POST',
|
||||
headers,
|
||||
body
|
||||
})
|
||||
if (!res.ok) {
|
||||
const error = await res.text()
|
||||
throw new Error(error)
|
||||
}
|
||||
|
||||
const payment = await res.json()
|
||||
return payment.serialized
|
||||
}
|
@ -3,13 +3,12 @@ import * as cln from 'wallets/cln/server'
|
||||
import * as lnAddr from 'wallets/lightning-address/server'
|
||||
import * as lnbits from 'wallets/lnbits/server'
|
||||
import * as nwc from 'wallets/nwc/server'
|
||||
import * as phoenixd from 'wallets/phoenixd/server'
|
||||
import { addWalletLog } from '@/api/resolvers/wallet'
|
||||
import walletDefs from 'wallets/server'
|
||||
import { parsePaymentRequest } from 'ln-service'
|
||||
import { toPositiveNumber } from '@/lib/validate'
|
||||
import { PAID_ACTION_TERMINAL_STATES } from '@/lib/constants'
|
||||
export default [lnd, cln, lnAddr, lnbits, nwc, phoenixd]
|
||||
export default [lnd, cln, lnAddr, lnbits, nwc]
|
||||
|
||||
const MAX_PENDING_INVOICES_PER_WALLET = 25
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user