Skip to content

Commit 3b235c4

Browse files
committed
chore: sync upstream main into vanish optimization branch
Resolve worker factory merge conflict by keeping vanish-aware UserRepository wiring and upstream NIP-05 repository wiring so vanish and gift-wrap flows remain compatible. Made-with: Cursor
2 parents c7e49d7 + f7869b0 commit 3b235c4

21 files changed

Lines changed: 1770 additions & 58 deletions

CONFIGURATION.md

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -119,4 +119,10 @@ Running `nostream` for the first time creates the settings file in `<project_roo
119119
| limits.message.ipWhitelist | List of IPs (IPv4 or IPv6) to ignore rate limits. |
120120
| limits.admissionCheck.rateLimits[].period | Rate limit period in milliseconds. |
121121
| limits.admissionCheck.rateLimits[].rate | Maximum number of admission checks during period. |
122-
| limits.admissionCheck.ipWhitelist | List of IPs (IPv4 or IPv6) to ignore rate limits. |
122+
| limits.admissionCheck.ipWhitelist | List of IPs (IPv4 or IPv6) to ignore rate limits. |
123+
| nip05.mode | NIP-05 verification mode: `enabled` requires verification, `passive` verifies without blocking, `disabled` does nothing. Defaults to `disabled`. |
124+
| nip05.verifyExpiration | Time in milliseconds before a successful NIP-05 verification expires and needs re-checking. Defaults to 604800000 (1 week). |
125+
| nip05.verifyUpdateFrequency | Minimum interval in milliseconds between re-verification attempts for a given author. Defaults to 86400000 (24 hours). |
126+
| nip05.maxConsecutiveFailures | Number of consecutive verification failures before giving up on an author. Defaults to 20. |
127+
| nip05.domainWhitelist | List of domains allowed for NIP-05 verification. If set, only authors verified at these domains can publish. |
128+
| nip05.domainBlacklist | List of domains blocked from NIP-05 verification. Authors with NIP-05 at these domains will be rejected. |
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
exports.up = function (knex) {
2+
return knex.schema.createTable('nip05_verifications', function (table) {
3+
table.binary('pubkey').notNullable().primary()
4+
table.text('nip05').notNullable()
5+
table.text('domain').notNullable()
6+
table.boolean('is_verified').notNullable().defaultTo(false)
7+
table.timestamp('last_verified_at', { useTz: true }).nullable()
8+
table.timestamp('last_checked_at', { useTz: true }).notNullable().defaultTo(knex.fn.now())
9+
table.integer('failure_count').notNullable().defaultTo(0)
10+
table.timestamp('created_at', { useTz: true }).notNullable().defaultTo(knex.fn.now())
11+
table.timestamp('updated_at', { useTz: true }).notNullable().defaultTo(knex.fn.now())
12+
13+
table.index(['domain'], 'idx_nip05_verifications_domain')
14+
table.index(['is_verified'], 'idx_nip05_verifications_is_verified')
15+
table.index(['last_checked_at'], 'idx_nip05_verifications_last_checked_at')
16+
})
17+
}
18+
19+
exports.down = function (knex) {
20+
return knex.schema.dropTable('nip05_verifications')
21+
}

package-lock.json

Lines changed: 49 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -31,8 +31,8 @@
3131
"prestart": "npm run build",
3232
"start": "cd dist && node src/index.js",
3333
"build:check": "npm run build -- --noEmit",
34-
"lint": "ESLINT_USE_FLAT_CONFIG=false eslint --ext .ts ./src ./test",
35-
"lint:report": "ESLINT_USE_FLAT_CONFIG=false eslint -o .lint-reports/eslint.json -f json --ext .ts ./src ./test",
34+
"lint": "cross-env ESLINT_USE_FLAT_CONFIG=false eslint --ext .ts ./src ./test",
35+
"lint:report": "cross-env ESLINT_USE_FLAT_CONFIG=false eslint -o .lint-reports/eslint.json -f json --ext .ts ./src ./test",
3636
"lint:fix": "npm run lint -- --fix",
3737
"knip": "knip --config .knip.json --production --no-progress --reporter compact",
3838
"check:all": "npm run lint && npm run knip",
@@ -81,6 +81,8 @@
8181
"@commitlint/config-conventional": "17.2.0",
8282
"@cucumber/cucumber": "10.2.1",
8383
"@cucumber/pretty-formatter": "1.0.0",
84+
"@eslint/eslintrc": "^3.3.1",
85+
"@eslint/js": "^9.39.1",
8486
"@semantic-release/commit-analyzer": "9.0.2",
8587
"@semantic-release/git": "10.0.1",
8688
"@semantic-release/github": "8.1.0",
@@ -98,13 +100,12 @@
98100
"@types/sinon": "^10.0.11",
99101
"@types/sinon-chai": "^3.2.8",
100102
"@types/ws": "^8.5.12",
101-
"@eslint/eslintrc": "^3.3.1",
102-
"@eslint/js": "^9.39.1",
103103
"@typescript-eslint/eslint-plugin": "^8.58.1",
104104
"@typescript-eslint/parser": "^8.58.1",
105105
"chai": "^4.3.6",
106106
"chai-as-promised": "^7.1.1",
107107
"conventional-changelog-conventionalcommits": "5.0.0",
108+
"cross-env": "^10.1.0",
108109
"cz-conventional-changelog": "3.3.0",
109110
"eslint": "^9.39.4",
110111
"husky": "8.0.2",
@@ -126,11 +127,11 @@
126127
},
127128
"dependencies": {
128129
"@noble/secp256k1": "1.7.1",
130+
"accepts": "^1.3.8",
129131
"axios": "^1.15.0",
130132
"bech32": "2.0.0",
131133
"debug": "4.3.4",
132134
"dotenv": "16.0.3",
133-
"accepts": "^1.3.8",
134135
"express": "4.22.1",
135136
"helmet": "6.0.1",
136137
"js-yaml": "4.1.1",

resources/default-settings.yaml

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,24 @@ paymentsProcessors:
3535
opennode:
3636
baseURL: api.opennode.com
3737
callbackBaseURL: https://nostream.your-domain.com/callbacks/opennode
38+
nip05:
39+
# NIP-05 verification of event authors as a spam reduction measure.
40+
# mode: 'enabled' requires NIP-05 for publishing (except kind 0),
41+
# 'passive' verifies but never blocks, 'disabled' does nothing.
42+
mode: disabled
43+
# How long (ms) a successful verification remains valid before re-check.
44+
# Matches nostr-rs-relay default of 1 week.
45+
verifyExpiration: 604800000
46+
# Minimum interval (ms) between re-verification attempts for a given author.
47+
# Matches nostr-rs-relay default of 24 hours.
48+
verifyUpdateFrequency: 86400000
49+
# How many consecutive failed checks before giving up on verifying an author.
50+
# Matches nostr-rs-relay default of 20.
51+
maxConsecutiveFailures: 20
52+
# Only allow authors with NIP-05 at these domains (empty = allow all)
53+
domainWhitelist: []
54+
# Block authors with NIP-05 at these domains
55+
domainBlacklist: []
3856
network:
3957
maxPayloadSize: 524288
4058
# Comment the next line if using CloudFlare proxy

src/@types/nip05.ts

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
import { Pubkey } from './base'
2+
3+
export interface Nip05Verification {
4+
pubkey: Pubkey
5+
nip05: string
6+
domain: string
7+
isVerified: boolean
8+
lastVerifiedAt: Date | null
9+
lastCheckedAt: Date
10+
failureCount: number
11+
createdAt: Date
12+
updatedAt: Date
13+
}
14+
15+
export interface DBNip05Verification {
16+
pubkey: Buffer
17+
nip05: string
18+
domain: string
19+
is_verified: boolean
20+
last_verified_at: Date | null
21+
last_checked_at: Date
22+
failure_count: number
23+
created_at: Date
24+
updated_at: Date
25+
}

src/@types/repositories.ts

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import { DBEvent, Event } from './event'
55
import { EventKinds } from '../constants/base'
66
import { EventKindsRange } from './settings'
77
import { Invoice } from './invoice'
8+
import { Nip05Verification } from './nip05'
89
import { SubscriptionFilter } from './subscription'
910
import { User } from './user'
1011

@@ -66,3 +67,14 @@ export interface IUserRepository {
6667
setVanished(pubkey: Pubkey, vanished: boolean, client?: DatabaseClient): Promise<number>
6768
admitUser(pubkey: Pubkey, admittedAt: Date, client?: DatabaseClient): Promise<void>
6869
}
70+
71+
export interface INip05VerificationRepository {
72+
findByPubkey(pubkey: Pubkey): Promise<Nip05Verification | undefined>
73+
upsert(verification: Nip05Verification): Promise<number>
74+
findPendingVerifications(
75+
updateFrequencyMs: number,
76+
maxFailures: number,
77+
limit: number,
78+
): Promise<Nip05Verification[]>
79+
deleteByPubkey(pubkey: Pubkey): Promise<number>
80+
}

0 commit comments

Comments
 (0)