@orangecheck/sdk 0.1.0 → 0.1.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/attestation.js +26 -2
- package/dist/attestation.js.map +1 -1
- package/dist/attestation.mjs +26 -2
- package/dist/attestation.mjs.map +1 -1
- package/dist/canonical.js +27 -5
- package/dist/canonical.js.map +1 -1
- package/dist/canonical.mjs +27 -5
- package/dist/canonical.mjs.map +1 -1
- package/dist/identity.js +130 -44
- package/dist/identity.js.map +1 -1
- package/dist/identity.mjs +130 -44
- package/dist/identity.mjs.map +1 -1
- package/dist/index.d.mts +7 -1
- package/dist/index.d.ts +7 -1
- package/dist/index.js +200 -57
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +199 -58
- package/dist/index.mjs.map +1 -1
- package/dist/verify.js +42 -8
- package/dist/verify.js.map +1 -1
- package/dist/verify.mjs +42 -8
- package/dist/verify.mjs.map +1 -1
- package/package.json +2 -1
package/dist/index.mjs
CHANGED
|
@@ -1,6 +1,9 @@
|
|
|
1
1
|
import { Buffer } from 'buffer';
|
|
2
2
|
import { Verifier } from 'bip322-js';
|
|
3
3
|
import * as bitcoinMessage from 'bitcoinjs-message';
|
|
4
|
+
import { schnorr } from '@noble/curves/secp256k1';
|
|
5
|
+
import { sha256 } from '@noble/hashes/sha2';
|
|
6
|
+
import { bech32 } from '@scure/base';
|
|
4
7
|
|
|
5
8
|
// src/canonical.ts
|
|
6
9
|
function toLowerHex(bytes) {
|
|
@@ -15,15 +18,27 @@ function randomNonce16BHexLower() {
|
|
|
15
18
|
}
|
|
16
19
|
} catch {
|
|
17
20
|
}
|
|
18
|
-
|
|
19
|
-
|
|
21
|
+
throw new Error("crypto.getRandomValues unavailable \u2014 refusing to mint a weak nonce");
|
|
22
|
+
}
|
|
23
|
+
var IDENTITY_PROTOCOL_RE = /^[a-z][a-z0-9_-]*$/;
|
|
24
|
+
var IDENTITY_FORBIDDEN_CHARS = /[\r\n,]/;
|
|
25
|
+
function assertSafeIdentity({ protocol, identifier }) {
|
|
26
|
+
if (!IDENTITY_PROTOCOL_RE.test(protocol)) {
|
|
27
|
+
throw new Error(
|
|
28
|
+
`invalid identity protocol: ${JSON.stringify(protocol)} \u2014 must match /^[a-z][a-z0-9_-]*$/`
|
|
29
|
+
);
|
|
30
|
+
}
|
|
31
|
+
if (!identifier || IDENTITY_FORBIDDEN_CHARS.test(identifier)) {
|
|
32
|
+
throw new Error(
|
|
33
|
+
`invalid identity identifier: ${JSON.stringify(identifier)} \u2014 must be non-empty and contain no newlines or commas`
|
|
34
|
+
);
|
|
20
35
|
}
|
|
21
|
-
return toLowerHex(arr);
|
|
22
36
|
}
|
|
23
37
|
function formatIdentities(identities = []) {
|
|
24
38
|
if (identities.length === 0) {
|
|
25
39
|
return "";
|
|
26
40
|
}
|
|
41
|
+
for (const id of identities) assertSafeIdentity(id);
|
|
27
42
|
const formatted = identities.map(({ protocol, identifier }) => `${protocol}:${identifier}`).sort();
|
|
28
43
|
return formatted.join(",");
|
|
29
44
|
}
|
|
@@ -31,7 +46,10 @@ function parseIdentities(identitiesStr) {
|
|
|
31
46
|
if (!identitiesStr || identitiesStr.trim() === "") {
|
|
32
47
|
return [];
|
|
33
48
|
}
|
|
34
|
-
|
|
49
|
+
if (IDENTITY_FORBIDDEN_CHARS.test(identitiesStr.replace(/,/g, ""))) {
|
|
50
|
+
throw new Error("identities field contains forbidden characters (newline)");
|
|
51
|
+
}
|
|
52
|
+
const bindings = identitiesStr.split(",").map((binding) => {
|
|
35
53
|
const colonIndex = binding.indexOf(":");
|
|
36
54
|
if (colonIndex === -1) {
|
|
37
55
|
throw new Error(`Invalid identity binding format: ${binding}`);
|
|
@@ -40,7 +58,14 @@ function parseIdentities(identitiesStr) {
|
|
|
40
58
|
protocol: binding.substring(0, colonIndex).trim(),
|
|
41
59
|
identifier: binding.substring(colonIndex + 1).trim()
|
|
42
60
|
};
|
|
43
|
-
})
|
|
61
|
+
});
|
|
62
|
+
for (const b of bindings) {
|
|
63
|
+
if (!b.protocol || !b.identifier) {
|
|
64
|
+
throw new Error(`Invalid identity binding: ${b.protocol}:${b.identifier}`);
|
|
65
|
+
}
|
|
66
|
+
assertSafeIdentity(b);
|
|
67
|
+
}
|
|
68
|
+
return bindings;
|
|
44
69
|
}
|
|
45
70
|
function buildCanonicalMessage({ address, identities }, extensions = {}) {
|
|
46
71
|
const nonce = randomNonce16BHexLower();
|
|
@@ -476,6 +501,21 @@ function isNip07Available() {
|
|
|
476
501
|
}
|
|
477
502
|
return !!window.nostr;
|
|
478
503
|
}
|
|
504
|
+
async function getNostrPublicKey() {
|
|
505
|
+
if (!isNip07Available()) {
|
|
506
|
+
log2.warn("NIP-07 extension not available");
|
|
507
|
+
return null;
|
|
508
|
+
}
|
|
509
|
+
try {
|
|
510
|
+
const nostr = window.nostr;
|
|
511
|
+
const pubkey = await nostr.getPublicKey();
|
|
512
|
+
log2.info({ pubkey }, "Got Nostr public key from NIP-07");
|
|
513
|
+
return pubkey;
|
|
514
|
+
} catch (err) {
|
|
515
|
+
log2.error({ error: err }, "Failed to get Nostr public key");
|
|
516
|
+
return null;
|
|
517
|
+
}
|
|
518
|
+
}
|
|
479
519
|
async function signNostrEvent(event) {
|
|
480
520
|
if (!isNip07Available()) {
|
|
481
521
|
log2.warn("NIP-07 extension not available");
|
|
@@ -491,6 +531,17 @@ async function signNostrEvent(event) {
|
|
|
491
531
|
return null;
|
|
492
532
|
}
|
|
493
533
|
}
|
|
534
|
+
function getNip07Info() {
|
|
535
|
+
if (!isNip07Available()) {
|
|
536
|
+
return { available: false };
|
|
537
|
+
}
|
|
538
|
+
const nostr = window.nostr;
|
|
539
|
+
return {
|
|
540
|
+
available: true,
|
|
541
|
+
name: nostr._metadata?.name,
|
|
542
|
+
version: nostr._metadata?.version
|
|
543
|
+
};
|
|
544
|
+
}
|
|
494
545
|
|
|
495
546
|
// src/attestation.ts
|
|
496
547
|
var log3 = createLogger("ocp/attestation");
|
|
@@ -751,7 +802,13 @@ async function verifySignature({
|
|
|
751
802
|
}
|
|
752
803
|
function parseCanonicalMessage(msg) {
|
|
753
804
|
const lines = msg.split("\n").map((l) => l.trim());
|
|
754
|
-
const getVal = (prefix) =>
|
|
805
|
+
const getVal = (prefix) => {
|
|
806
|
+
const needle = prefix + ":";
|
|
807
|
+
const hit = lines.find((l) => l.toLowerCase().startsWith(needle));
|
|
808
|
+
if (!hit) return void 0;
|
|
809
|
+
const idx = hit.indexOf(":");
|
|
810
|
+
return hit.slice(idx + 1).trim();
|
|
811
|
+
};
|
|
755
812
|
const address = getVal("address") || "";
|
|
756
813
|
const identitiesStr = getVal("identities") || "";
|
|
757
814
|
let identities = [];
|
|
@@ -806,8 +863,7 @@ async function getAddressUtxos(address, network, opts) {
|
|
|
806
863
|
const resp = await fetch(url, {
|
|
807
864
|
method: "GET",
|
|
808
865
|
headers: { Accept: "application/json" },
|
|
809
|
-
signal: AbortSignal.timeout(
|
|
810
|
-
// 10s timeout
|
|
866
|
+
signal: AbortSignal.timeout(5e3)
|
|
811
867
|
});
|
|
812
868
|
if (!resp.ok) {
|
|
813
869
|
throw new Error(`HTTP ${resp.status}`);
|
|
@@ -912,13 +968,18 @@ async function verify2(input, opts = {}) {
|
|
|
912
968
|
codes.push("network_testmode");
|
|
913
969
|
return { ok: false, codes, network, attestation_id };
|
|
914
970
|
}
|
|
915
|
-
if (opts.expectedAud
|
|
916
|
-
|
|
971
|
+
if (opts.expectedAud) {
|
|
972
|
+
const aud = parsed.extensions["aud"];
|
|
973
|
+
if (!aud || aud !== opts.expectedAud) {
|
|
974
|
+
codes.push("aud_mismatch");
|
|
975
|
+
return { ok: false, codes, network, attestation_id };
|
|
976
|
+
}
|
|
917
977
|
}
|
|
918
978
|
if (parsed.extensions["expires"]) {
|
|
919
979
|
const exp = Date.parse(parsed.extensions["expires"]);
|
|
920
980
|
if (!Number.isNaN(exp) && exp < Date.now()) {
|
|
921
981
|
codes.push("expired");
|
|
982
|
+
return { ok: false, codes, network, attestation_id };
|
|
922
983
|
}
|
|
923
984
|
}
|
|
924
985
|
const sigCode = await verifySignature({
|
|
@@ -996,7 +1057,7 @@ async function verify2(input, opts = {}) {
|
|
|
996
1057
|
metrics
|
|
997
1058
|
};
|
|
998
1059
|
} catch (utxoError) {
|
|
999
|
-
|
|
1060
|
+
log4.error({ err: utxoError }, "UTXO fetch failed");
|
|
1000
1061
|
codes.push("bad_request");
|
|
1001
1062
|
return { ok: false, codes, network, attestation_id };
|
|
1002
1063
|
}
|
|
@@ -1246,9 +1307,25 @@ var identityVerificationLimiter = createRateLimiter(5, 6e4);
|
|
|
1246
1307
|
|
|
1247
1308
|
// src/identity/dns.ts
|
|
1248
1309
|
var log5 = createLogger("identity-verification/dns");
|
|
1310
|
+
var PRIVATE_HOST_RE = /^(?:localhost|.*\.local|.*\.internal|.*\.localhost|.*\.lan|.*\.home|.*\.arpa|\[?::1\]?|\[?::\]?)$/i;
|
|
1311
|
+
var PRIVATE_IPV4_RE = /^(?:10\.|127\.|169\.254\.|192\.168\.|172\.(?:1[6-9]|2\d|3[01])\.|0\.|100\.(?:6[4-9]|[7-9]\d|1[01]\d|12[0-7])\.|22[4-9]\.|23\d\.|24\d\.|25[0-5]\.)/;
|
|
1312
|
+
var WELL_KNOWN_TIMEOUT_MS = 5e3;
|
|
1313
|
+
function isSafePublicHost(host) {
|
|
1314
|
+
const h = host.toLowerCase();
|
|
1315
|
+
if (PRIVATE_HOST_RE.test(h)) return false;
|
|
1316
|
+
if (PRIVATE_IPV4_RE.test(h)) return false;
|
|
1317
|
+
if (h.startsWith("[") || /^[0-9a-f:]+$/.test(h)) return false;
|
|
1318
|
+
return true;
|
|
1319
|
+
}
|
|
1249
1320
|
async function verifyDnsIdentity(attestationId, domain) {
|
|
1250
1321
|
log5.info({ attestationId, domain }, "Verifying DNS identity");
|
|
1251
1322
|
const cleanDomain = domain.replace(/^https?:\/\//, "").replace(/\/$/, "");
|
|
1323
|
+
if (!isValidDomain(cleanDomain)) {
|
|
1324
|
+
return { verified: false, error: `invalid domain format: ${cleanDomain}` };
|
|
1325
|
+
}
|
|
1326
|
+
if (!isSafePublicHost(cleanDomain)) {
|
|
1327
|
+
return { verified: false, error: "domain resolves to a disallowed private host" };
|
|
1328
|
+
}
|
|
1252
1329
|
const wellKnownResult = await checkWellKnownFile(attestationId, cleanDomain);
|
|
1253
1330
|
if (wellKnownResult.verified) {
|
|
1254
1331
|
return wellKnownResult;
|
|
@@ -1260,38 +1337,31 @@ async function verifyDnsIdentity(attestationId, domain) {
|
|
|
1260
1337
|
};
|
|
1261
1338
|
}
|
|
1262
1339
|
async function checkWellKnownFile(attestationId, domain) {
|
|
1263
|
-
const
|
|
1264
|
-
|
|
1265
|
-
|
|
1266
|
-
|
|
1267
|
-
|
|
1268
|
-
|
|
1269
|
-
|
|
1270
|
-
|
|
1271
|
-
|
|
1272
|
-
|
|
1273
|
-
|
|
1274
|
-
|
|
1275
|
-
|
|
1276
|
-
|
|
1277
|
-
|
|
1278
|
-
|
|
1279
|
-
|
|
1280
|
-
|
|
1281
|
-
|
|
1282
|
-
|
|
1283
|
-
|
|
1284
|
-
verified: true,
|
|
1285
|
-
method: "well-known",
|
|
1286
|
-
url
|
|
1287
|
-
};
|
|
1288
|
-
} else {
|
|
1289
|
-
log5.info({ domain, url }, "Well-known file exists but no attestation ID found");
|
|
1290
|
-
}
|
|
1340
|
+
const url = `https://${domain}/.well-known/orangecheck.txt`;
|
|
1341
|
+
try {
|
|
1342
|
+
log5.info({ url }, "Checking well-known file");
|
|
1343
|
+
const response = await fetch(url, {
|
|
1344
|
+
method: "GET",
|
|
1345
|
+
headers: { Accept: "text/plain" },
|
|
1346
|
+
// Don't follow redirects to other domains
|
|
1347
|
+
redirect: "manual",
|
|
1348
|
+
signal: AbortSignal.timeout(WELL_KNOWN_TIMEOUT_MS)
|
|
1349
|
+
});
|
|
1350
|
+
if (response.ok) {
|
|
1351
|
+
const content = await response.text();
|
|
1352
|
+
if (content.includes(attestationId)) {
|
|
1353
|
+
log5.info({ domain, url }, "Found attestation ID in well-known file");
|
|
1354
|
+
return {
|
|
1355
|
+
verified: true,
|
|
1356
|
+
method: "well-known",
|
|
1357
|
+
url
|
|
1358
|
+
};
|
|
1359
|
+
} else {
|
|
1360
|
+
log5.info({ domain, url }, "Well-known file exists but no attestation ID found");
|
|
1291
1361
|
}
|
|
1292
|
-
} catch (err) {
|
|
1293
|
-
log5.warn({ error: err, url }, "Failed to fetch well-known file");
|
|
1294
1362
|
}
|
|
1363
|
+
} catch (err) {
|
|
1364
|
+
log5.warn({ error: err, url }, "Failed to fetch well-known file");
|
|
1295
1365
|
}
|
|
1296
1366
|
return {
|
|
1297
1367
|
verified: false,
|
|
@@ -1364,14 +1434,32 @@ function isDnsIdentityVerified(attestationId, _domain, cachedContent) {
|
|
|
1364
1434
|
|
|
1365
1435
|
// src/identity/github.ts
|
|
1366
1436
|
var log6 = createLogger("identity-verification/github");
|
|
1437
|
+
var GITHUB_GIST_RAW_HOST = "gist.githubusercontent.com";
|
|
1438
|
+
var MAX_GISTS_SCANNED = 30;
|
|
1439
|
+
var MAX_FILES_PER_GIST = 10;
|
|
1440
|
+
var FETCH_TIMEOUT_MS = 5e3;
|
|
1441
|
+
var GITHUB_USERNAME_RE = /^[a-zA-Z0-9](?:[a-zA-Z0-9]|-(?=[a-zA-Z0-9])){0,38}$/;
|
|
1442
|
+
function isSafeGistRawUrl(raw) {
|
|
1443
|
+
try {
|
|
1444
|
+
const u = new URL(raw);
|
|
1445
|
+
return u.protocol === "https:" && u.hostname === GITHUB_GIST_RAW_HOST;
|
|
1446
|
+
} catch {
|
|
1447
|
+
return false;
|
|
1448
|
+
}
|
|
1449
|
+
}
|
|
1367
1450
|
async function verifyGitHubIdentity(attestationId, username) {
|
|
1368
1451
|
log6.info({ attestationId, username }, "Verifying GitHub identity");
|
|
1452
|
+
if (!GITHUB_USERNAME_RE.test(username)) {
|
|
1453
|
+
return { verified: false, error: "invalid GitHub username format" };
|
|
1454
|
+
}
|
|
1369
1455
|
try {
|
|
1370
|
-
const response = await fetch(
|
|
1371
|
-
|
|
1372
|
-
|
|
1456
|
+
const response = await fetch(
|
|
1457
|
+
`https://api.github.com/users/${encodeURIComponent(username)}/gists?per_page=${MAX_GISTS_SCANNED}`,
|
|
1458
|
+
{
|
|
1459
|
+
headers: { Accept: "application/vnd.github.v3+json" },
|
|
1460
|
+
signal: AbortSignal.timeout(FETCH_TIMEOUT_MS)
|
|
1373
1461
|
}
|
|
1374
|
-
|
|
1462
|
+
);
|
|
1375
1463
|
if (!response.ok) {
|
|
1376
1464
|
if (response.status === 404) {
|
|
1377
1465
|
return {
|
|
@@ -1386,7 +1474,7 @@ async function verifyGitHubIdentity(attestationId, username) {
|
|
|
1386
1474
|
}
|
|
1387
1475
|
const gists = await response.json();
|
|
1388
1476
|
log6.info({ username, gistCount: gists.length }, "Fetched GitHub gists");
|
|
1389
|
-
for (const gist of gists) {
|
|
1477
|
+
for (const gist of gists.slice(0, MAX_GISTS_SCANNED)) {
|
|
1390
1478
|
if (gist.description?.includes(attestationId)) {
|
|
1391
1479
|
log6.info({ username, gistId: gist.id }, "Found attestation ID in gist description");
|
|
1392
1480
|
return {
|
|
@@ -1395,7 +1483,8 @@ async function verifyGitHubIdentity(attestationId, username) {
|
|
|
1395
1483
|
gistId: gist.id
|
|
1396
1484
|
};
|
|
1397
1485
|
}
|
|
1398
|
-
|
|
1486
|
+
const files = Object.entries(gist.files).slice(0, MAX_FILES_PER_GIST);
|
|
1487
|
+
for (const [filename, file] of files) {
|
|
1399
1488
|
if (file.content && file.content.includes(attestationId)) {
|
|
1400
1489
|
log6.info(
|
|
1401
1490
|
{ username, gistId: gist.id, filename },
|
|
@@ -1407,8 +1496,17 @@ async function verifyGitHubIdentity(attestationId, username) {
|
|
|
1407
1496
|
gistId: gist.id
|
|
1408
1497
|
};
|
|
1409
1498
|
}
|
|
1499
|
+
if (!isSafeGistRawUrl(file.raw_url)) {
|
|
1500
|
+
log6.warn(
|
|
1501
|
+
{ filename, rawUrl: file.raw_url },
|
|
1502
|
+
"skipping gist file: raw_url failed allow-list"
|
|
1503
|
+
);
|
|
1504
|
+
continue;
|
|
1505
|
+
}
|
|
1410
1506
|
try {
|
|
1411
|
-
const fileResponse = await fetch(file.raw_url
|
|
1507
|
+
const fileResponse = await fetch(file.raw_url, {
|
|
1508
|
+
signal: AbortSignal.timeout(FETCH_TIMEOUT_MS)
|
|
1509
|
+
});
|
|
1412
1510
|
if (fileResponse.ok) {
|
|
1413
1511
|
const content = await fileResponse.text();
|
|
1414
1512
|
if (content.includes(attestationId)) {
|
|
@@ -1486,15 +1584,38 @@ function isGitHubIdentityVerified(attestationId, _username, cachedGists) {
|
|
|
1486
1584
|
function getGistCreationUrl() {
|
|
1487
1585
|
return "https://gist.github.com/";
|
|
1488
1586
|
}
|
|
1489
|
-
|
|
1490
|
-
// src/identity/nostr.ts
|
|
1491
1587
|
var log7 = createLogger("identity-verification/nostr");
|
|
1588
|
+
var HEX_64_RE = /^[0-9a-f]{64}$/;
|
|
1589
|
+
function toHex(bytes) {
|
|
1590
|
+
let out = "";
|
|
1591
|
+
for (const b of bytes) out += b.toString(16).padStart(2, "0");
|
|
1592
|
+
return out;
|
|
1593
|
+
}
|
|
1594
|
+
function fromHex(hex) {
|
|
1595
|
+
if (hex.length % 2 !== 0) throw new Error("odd-length hex");
|
|
1596
|
+
const out = new Uint8Array(hex.length / 2);
|
|
1597
|
+
for (let i = 0; i < out.length; i++) {
|
|
1598
|
+
out[i] = parseInt(hex.slice(i * 2, i * 2 + 2), 16);
|
|
1599
|
+
}
|
|
1600
|
+
return out;
|
|
1601
|
+
}
|
|
1492
1602
|
function npubToHex(npub) {
|
|
1493
|
-
|
|
1494
|
-
|
|
1603
|
+
const trimmed = npub.trim();
|
|
1604
|
+
if (HEX_64_RE.test(trimmed.toLowerCase())) {
|
|
1605
|
+
return trimmed.toLowerCase();
|
|
1606
|
+
}
|
|
1607
|
+
if (!trimmed.toLowerCase().startsWith("npub1")) {
|
|
1608
|
+
throw new Error(`not an npub: ${trimmed.slice(0, 12)}\u2026`);
|
|
1495
1609
|
}
|
|
1496
|
-
|
|
1497
|
-
|
|
1610
|
+
const decoded = bech32.decode(trimmed.toLowerCase(), 1023);
|
|
1611
|
+
if (decoded.prefix !== "npub") {
|
|
1612
|
+
throw new Error(`bech32 prefix mismatch: expected npub, got ${decoded.prefix}`);
|
|
1613
|
+
}
|
|
1614
|
+
const bytes = bech32.fromWords(decoded.words);
|
|
1615
|
+
if (bytes.length !== 32) {
|
|
1616
|
+
throw new Error(`invalid npub payload length: ${bytes.length}`);
|
|
1617
|
+
}
|
|
1618
|
+
return toHex(Uint8Array.from(bytes));
|
|
1498
1619
|
}
|
|
1499
1620
|
async function queryNostrEvents(options) {
|
|
1500
1621
|
const { authors, kinds, search, relays = DEFAULT_RELAYS, limit = 100 } = options;
|
|
@@ -1565,11 +1686,31 @@ async function queryNostrEvents(options) {
|
|
|
1565
1686
|
return events;
|
|
1566
1687
|
}
|
|
1567
1688
|
async function verifyNostrEventSignature(event) {
|
|
1568
|
-
|
|
1689
|
+
try {
|
|
1690
|
+
if (!event.id || !event.sig || !event.pubkey || typeof event.id !== "string" || typeof event.sig !== "string" || typeof event.pubkey !== "string" || event.sig.length !== 128 || !HEX_64_RE.test(event.id) || !HEX_64_RE.test(event.pubkey)) {
|
|
1691
|
+
return false;
|
|
1692
|
+
}
|
|
1693
|
+
const preimage = JSON.stringify([
|
|
1694
|
+
0,
|
|
1695
|
+
event.pubkey,
|
|
1696
|
+
event.created_at,
|
|
1697
|
+
event.kind,
|
|
1698
|
+
event.tags ?? [],
|
|
1699
|
+
event.content ?? ""
|
|
1700
|
+
]);
|
|
1701
|
+
const computedId = toHex(sha256(new TextEncoder().encode(preimage)));
|
|
1702
|
+
if (computedId !== event.id.toLowerCase()) {
|
|
1703
|
+
log7.warn(
|
|
1704
|
+
{ eventId: event.id, computedId },
|
|
1705
|
+
"nostr event id does not match its content"
|
|
1706
|
+
);
|
|
1707
|
+
return false;
|
|
1708
|
+
}
|
|
1709
|
+
return schnorr.verify(fromHex(event.sig), fromHex(event.id), fromHex(event.pubkey));
|
|
1710
|
+
} catch (err) {
|
|
1711
|
+
log7.warn({ err }, "schnorr verify threw");
|
|
1569
1712
|
return false;
|
|
1570
1713
|
}
|
|
1571
|
-
log7.warn("Nostr signature verification not fully implemented");
|
|
1572
|
-
return true;
|
|
1573
1714
|
}
|
|
1574
1715
|
async function verifyNostrIdentity(attestationId, npub, relays) {
|
|
1575
1716
|
log7.info({ attestationId, npub }, "Verifying Nostr identity");
|
|
@@ -1925,6 +2066,6 @@ var STATUS_META = {
|
|
|
1925
2066
|
}
|
|
1926
2067
|
};
|
|
1927
2068
|
|
|
1928
|
-
export { DEFAULT_RELAYS, STATUS_META, buildCanonicalMessage, check, computeScore, createAttestation, createAttestationEnvelope, createAttestationEvent, discoverAttestations, formatIdentities, generateAttestationId, generateGistTemplate, generateTweetText, generateWellKnownContent, getAttestationsForAddress, getAttestationsForIdentity, getDnsVerificationInstructions, getGistCreationUrl, getGitHubVerificationInstructions, getManualVerificationInstructions, getNostrVerificationInstructions, getTweetUrl, getTwitterComposeUrl, getTwitterVerificationInstructions, getVerificationInstructions, getVerificationSummary, getWellKnownUrl, isDnsIdentityVerified, isGitHubIdentityVerified, isNip07Available, isNostrIdentityVerified, isValidDomain, isValidTweetUrl, issueChallenge, parseAttestationFromEvent, parseIdentities, publishAttestation, publishToRelays, queryByAddress, queryByAttestationId, queryByIdentity, requiresManualVerification, signNostrEvent, supportsAutomaticVerification, verify2 as verify, verifyAllIdentities, verifyAttestationById, verifyChallenge, verifyDnsIdentity, verifyGitHubIdentity, verifyIdentity, verifyNostrIdentity, verifyTwitterIdentity };
|
|
2069
|
+
export { DEFAULT_RELAYS, STATUS_META, buildCanonicalMessage, check, computeScore, createAttestation, createAttestationEnvelope, createAttestationEvent, discoverAttestations, formatIdentities, generateAttestationId, generateGistTemplate, generateTweetText, generateWellKnownContent, getAttestationsForAddress, getAttestationsForIdentity, getDnsVerificationInstructions, getGistCreationUrl, getGitHubVerificationInstructions, getManualVerificationInstructions, getNip07Info, getNostrPublicKey, getNostrVerificationInstructions, getTweetUrl, getTwitterComposeUrl, getTwitterVerificationInstructions, getVerificationInstructions, getVerificationSummary, getWellKnownUrl, isDnsIdentityVerified, isGitHubIdentityVerified, isNip07Available, isNostrIdentityVerified, isValidDomain, isValidTweetUrl, issueChallenge, parseAttestationFromEvent, parseIdentities, publishAttestation, publishToRelays, queryByAddress, queryByAttestationId, queryByIdentity, requiresManualVerification, signNostrEvent, supportsAutomaticVerification, verify2 as verify, verifyAllIdentities, verifyAttestationById, verifyChallenge, verifyDnsIdentity, verifyGitHubIdentity, verifyIdentity, verifyNostrIdentity, verifyTwitterIdentity };
|
|
1929
2070
|
//# sourceMappingURL=index.mjs.map
|
|
1930
2071
|
//# sourceMappingURL=index.mjs.map
|