From 703aafc587d618f97a4b19236b3d6e5716a92e5f Mon Sep 17 00:00:00 2001 From: jawndiego Date: Tue, 26 Mar 2024 17:50:03 -0400 Subject: [PATCH 01/18] first pass at syndicate integration --- apps/site/app/api/post/route.ts | 89 ++++++++++++--- apps/site/app/api/postBatch/route.ts | 107 ++++++++++++----- apps/site/app/api/registerFor/route.ts | 152 ++++++++++++++++--------- apps/site/config/syndicateClient.ts | 11 ++ apps/site/package.json | 1 + pnpm-lock.yaml | 40 +++++++ 6 files changed, 303 insertions(+), 97 deletions(-) create mode 100644 apps/site/config/syndicateClient.ts diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index 7b0b9524..33441048 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -4,35 +4,90 @@ import { ethers } from 'ethers' import type { NextRequest } from 'next/server' import { addresses, postGatewayABI } from 'scrypt' import type { Hex } from 'viem' +import { syndicate } from '@/config/syndicateClient' + +interface TransactionAttempt { + block: number + blockCreatedAt: string + chainId: number + createdAt: string + hash: string + nonce: number + reverted: boolean + signedTxn: string + status: string + transactionId: string + updatedAt: string + walletAddress: string +} + +interface SyndicateApiResponse { + chainId: number + contractAddress: string + createdAt: string + data: string + decodedData: object + functionSignature: string + invalid: boolean + projectId: string + transactionAttempts: TransactionAttempt[] + transactionId: string + updatedAt: string + value: string +} + export async function POST(req: NextRequest) { const post = await req.json() - const credentials = { - relayerApiKey: process.env.NONCE_API_UNO, - relayerApiSecret: process.env.NONCE_SECRET_UNO, - } + // const credentials = { + // relayerApiKey: process.env.NONCE_API_UNO, + // relayerApiSecret: process.env.NONCE_SECRET_UNO, + // } try { - const defenderClient = new Defender(credentials) - const provider = defenderClient.relaySigner.getProvider() - const signer = defenderClient.relaySigner.getSigner(provider, { - speed: 'fast', - }) + // const defenderClient = new Defender(credentials) + // const provider = defenderClient.relaySigner.getProvider() + // const signer = defenderClient.relaySigner.getSigner(provider, { + // speed: 'fast', + // }) const postGateway = new ethers.Contract( addresses.postGateway.nova, - postGatewayABI, - signer as unknown as ethers.Signer, - ) + postGatewayABI) - const tx = await postGateway.post(post) + const postTx = await syndicate.transact.sendTransaction({ + projectId: 'a8349c10-aafd-4785-95f3-bbada9784910', + contractAddress: '0x423a602F5e551A25b28eb33eB56B961590aD5290', + chainId: 42070, + functionSignature: 'post()', + args: post + }) + + // const tx = await postGateway.post(post) - await novaPubClient.waitForTransactionReceipt({ - hash: tx.hash as Hex, - }) + // await novaPubClient.waitForTransactionReceipt({ + // hash: tx.hash as Hex, + // }) + + const projectId = process.env.SYNDICATE_PROJECT_ID + if (!projectId) { + throw new Error("SYNDICATE_PROJECT_ID is not defined in environment variables.") + } + + const options = { method: 'GET', headers: { Authorization: 'Bearer ' } }; + + const txResponse: SyndicateApiResponse = await fetch(`https://api.syndicate.io/wallet/project/${projectId}/request/${postTx.transactionId}`, options) + .then(response => response.json()) + .catch(err => console.error(err)) + + if (!txResponse || !txResponse.transactionAttempts.length) { + throw new Error("Transaction attempt data not found.") + } + + const txHash = txResponse.transactionAttempts[0].hash - return new Response(JSON.stringify({ success: true, hash: tx.hash }), { + return new Response(JSON.stringify({ success: true, hash: txHash }), { status: 200, headers: { 'Content-Type': 'application/json' }, }) diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index 4a21bc94..25f476fb 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -1,58 +1,113 @@ -import { novaPubClient } from '@/config/publicClient' -import { Defender } from '@openzeppelin/defender-sdk' -import { ethers } from 'ethers' -import type { NextRequest } from 'next/server' -import { addresses, postGatewayABI } from 'scrypt' -import type { Hex } from 'viem' +import { novaPubClient } from "@/config/publicClient" +import { Defender } from "@openzeppelin/defender-sdk" +import { ethers } from "ethers" +import type { NextRequest } from "next/server" +import { addresses, postGatewayABI } from "scrypt" +import type { Hex } from "viem" +import { syndicate } from "@/config/syndicateClient" + +interface TransactionAttempt { + block: number + blockCreatedAt: string + chainId: number + createdAt: string + hash: string + nonce: number + reverted: boolean + signedTxn: string + status: string + transactionId: string + updatedAt: string + walletAddress: string +} + +interface SyndicateApiResponse { + chainId: number + contractAddress: string + createdAt: string + data: string + decodedData: object + functionSignature: string + invalid: boolean + projectId: string + transactionAttempts: TransactionAttempt[] + transactionId: string + updatedAt: string + value: string +} export async function POST(req: NextRequest) { const postsArray = await req.json() console.log({ postsArray }) - const credentials = { - relayerApiKey: process.env.NONCE_API_UNO, - relayerApiSecret: process.env.NONCE_SECRET_UNO, - } + // const credentials = { + // relayerApiKey: process.env.NONCE_API_UNO, + // relayerApiSecret: process.env.NONCE_SECRET_UNO, + // } try { - const defenderClient = new Defender(credentials) - const provider = defenderClient.relaySigner.getProvider() - const signer = defenderClient.relaySigner.getSigner(provider, { - speed: 'fast', - }) + // const defenderClient = new Defender(credentials) + // const provider = defenderClient.relaySigner.getProvider() + // const signer = defenderClient.relaySigner.getSigner(provider, { + // speed: 'fast', + // }) const postGateway = new ethers.Contract( addresses.postGateway.nova, - postGatewayABI, - signer as unknown as ethers.Signer, + postGatewayABI ) - const tx = await postGateway.postBatch(postsArray) - await novaPubClient.waitForTransactionReceipt({ - hash: tx.hash as Hex, + const projectId = process.env.SYNDICATE_PROJECT_ID + if (!projectId) { + throw new Error("SYNDICATE_PROJECT_ID is not defined in environment variables.") + } + const postBatchTx = await syndicate.transact.sendTransaction({ + projectId: projectId, + contractAddress: addresses.postGateway.nova, + chainId: 42170, + functionSignature: + "postBatch((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig)[] posts)", + args: postsArray }) - return new Response(JSON.stringify({ success: true, hash: tx.hash }), { + const options = { method: 'GET', headers: { Authorization: 'Bearer ' } }; + + const txResponse: SyndicateApiResponse = await fetch(`https://api.syndicate.io/wallet/project/${projectId}/request/${postBatchTx.transactionId}`, options) + .then(response => response.json()) + .catch(err => console.error(err)) + + // const tx = await postGateway.postBatch(postsArray) + // await novaPubClient.waitForTransactionReceipt({ + // hash: tx.hash as Hex, + // }) + + if (!txResponse || !txResponse.transactionAttempts.length) { + throw new Error("Transaction attempt data not found.") + } + + const txHash = txResponse.transactionAttempts[0].hash + + return new Response(JSON.stringify({ success: true, hash: txHash}), { status: 200, - headers: { 'Content-Type': 'application/json' }, + headers: { "Content-Type": "application/json" }, }) } catch (error) { - let errorMessage = 'Unknown error' + let errorMessage = "Unknown error" let statusCode = 500 if (error instanceof Error) { errorMessage = error.message statusCode = // biome-ignore lint: `status` is not part of the standard Error interface - typeof (error as any).status === 'number' ? (error as any).status : 500 + typeof (error as any).status === "number" ? (error as any).status : 500 } return new Response( JSON.stringify({ success: false, hash: null, error: errorMessage }), { status: statusCode, - headers: { 'Content-Type': 'application/json' }, - }, + headers: { "Content-Type": "application/json" }, + } ) } } diff --git a/apps/site/app/api/registerFor/route.ts b/apps/site/app/api/registerFor/route.ts index 648d0ff5..ef3cac19 100644 --- a/apps/site/app/api/registerFor/route.ts +++ b/apps/site/app/api/registerFor/route.ts @@ -4,6 +4,38 @@ import { ethers } from 'ethers' import type { NextRequest } from 'next/server' import { addresses, idRegistryABI } from 'scrypt' import { type Hex, decodeAbiParameters } from 'viem' +import { syndicate } from '@/config/syndicateClient' + + +interface SyndicateApiResponse { + chainId: number + contractAddress: string + createdAt: string + data: string + decodedData: object + functionSignature: string + invalid: boolean + projectId: string + transactionAttempts: TransactionAttempt[] + transactionId: string + updatedAt: string + value: string +} + +interface TransactionAttempt { + block: number + blockCreatedAt: string + chainId: number + createdAt: string + hash: string + nonce: number + reverted: boolean + signedTxn: string + status: string + transactionId: string + updatedAt: string + walletAddress: string +} export async function POST(req: NextRequest) { const user = await req.json() @@ -13,57 +45,74 @@ export async function POST(req: NextRequest) { const { to, recovery, deadline, sig } = userWithoutUsername console.log({ userWithoutUsername }) - const credentials = { - relayerApiKey: process.env.IDREGISTRY_API_UNO, - relayerApiSecret: process.env.IDREGISTRY_SECRET_UNO, - } + + // const credentials = { + // relayerApiKey: process.env.IDREGISTRY_API_UNO, + // relayerApiSecret: process.env.IDREGISTRY_SECRET_UNO, + // } + try { - const defenderClient = new Defender(credentials) - const provider = defenderClient.relaySigner.getProvider() - const signer = defenderClient.relaySigner.getSigner(provider, { - speed: 'fast', - }) + // const defenderClient = new Defender(credentials) + // const provider = defenderClient.relaySigner.getProvider() + // const signer = defenderClient.relaySigner.getSigner(provider, { + // speed: 'fast', + // }) const idRegistry = new ethers.Contract( addresses.idRegistry.optimism, - idRegistryABI, - signer as unknown as ethers.Signer, - ) - - const registerTxn = await idRegistry.registerFor( - to, - recovery, - deadline, - sig, - ) - - const txnReceipt = await optimismPubClient.waitForTransactionReceipt({ - hash: registerTxn.hash as Hex, + idRegistryABI, + ) + + // const registerTxn = await idRegistry.registerFor( + // to, + // recovery, + // deadline, + // sig, + // ) + + const projectId = process.env.SYNDICATE_PROJECT_ID + if (!projectId) { + throw new Error("SYNDICATE_PROJECT_ID is not defined in environment variables.") + } + + const registerTx = await syndicate.transact.sendTransaction({ + projectId: projectId, + contractAddress: addresses.idRegistry.optimism, + chainId: 420, + functionSignature: 'registerFor(address to, address recovery, uint256 deadline, bytes sig)', + args: userWithoutUsername }) - const [rid, recoveryAddress] = decodeAbiParameters( - [ - { name: 'rid', type: 'uint256' }, - { name: 'recoveryAddress', type: 'address' }, - ], - txnReceipt.logs[0].data, - ) - - console.log('rid: ', rid) - console.log('transaction receipt: ', registerTxn) - - return new Response( - JSON.stringify({ - success: true, - hash: registerTxn.hash, - rid: rid.toString(), - }), - { - status: 200, - headers: { 'Content-Type': 'application/json' }, - }, - ) + // const txnReceipt = await optimismPubClient.waitForTransactionReceipt({ + // hash: registerTxn.hash as Hex, + // }) + + // const [rid, recoveryAddress] = decodeAbiParameters( + // [ + // { name: 'rid', type: 'uint256' }, + // { name: 'recoveryAddress', type: 'address' }, + // ], + // txnReceipt.logs[0].data, + // ) + + // console.log('rid: ', rid) + console.log('transaction receipt: ', registerTx) + + const options = { method: 'GET', headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}` } } + const txResponse: SyndicateApiResponse = await fetch(`https://api.syndicate.io/wallet/project/${projectId}/request/${registerTx.transactionId}`, options) + .then(response => response.json()) + + if (!txResponse || !txResponse.transactionAttempts.length) { + throw new Error("Transaction attempt data not found.") + } + + const txHash = txResponse.transactionAttempts[0].hash + + return new Response(JSON.stringify({ success: true, hash: txHash }), { + status: 200, + headers: { 'Content-Type': 'application/json' }, + }) } catch (error) { console.error(error) let errorMessage = 'Unknown error' @@ -71,17 +120,12 @@ export async function POST(req: NextRequest) { if (error instanceof Error) { errorMessage = error.message - statusCode = - // biome-ignore lint: `status` is not part of the standard Error interface - typeof (error as any).status === 'number' ? (error as any).status : 500 + statusCode = typeof (error as any).status === 'number' ? (error as any).status : 500 } - return new Response( - JSON.stringify({ success: false, error: errorMessage }), - { - status: statusCode, - headers: { 'Content-Type': 'application/json' }, - }, - ) + return new Response(JSON.stringify({ success: false, error: errorMessage }), { + status: statusCode, + headers: { 'Content-Type': 'application/json' }, + }) } } diff --git a/apps/site/config/syndicateClient.ts b/apps/site/config/syndicateClient.ts new file mode 100644 index 00000000..7e8ab24f --- /dev/null +++ b/apps/site/config/syndicateClient.ts @@ -0,0 +1,11 @@ +import { SyndicateClient } from "@syndicateio/syndicate-node"; + +export const syndicate = new SyndicateClient({ + token: () => { + const apiKey = process.env.SYNDICATE_API_KEY + if (typeof apiKey === "undefined") { + throw new Error("SYNDICATE_API_KEY is not defined in environment variables.") + } + return apiKey; + }, + }); \ No newline at end of file diff --git a/apps/site/package.json b/apps/site/package.json index b801decb..bbf635c8 100644 --- a/apps/site/package.json +++ b/apps/site/package.json @@ -29,6 +29,7 @@ "@radix-ui/react-popover": "^1.0.7", "@radix-ui/react-separator": "^1.0.3", "@radix-ui/react-slot": "^1.0.2", + "@syndicateio/syndicate-node": "^0.0.449", "@vercel/analytics": "^1.0.2", "@vercel/kv": "^1.0.0", "base64url": "^3.0.1", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index d94d2ff4..b3c114f7 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -130,6 +130,9 @@ importers: '@radix-ui/react-slot': specifier: ^1.0.2 version: 1.0.2(@types/react@18.2.21)(react@18.2.0) + '@syndicateio/syndicate-node': + specifier: ^0.0.449 + version: 0.0.449 '@vercel/analytics': specifier: ^1.0.2 version: 1.0.2 @@ -4927,6 +4930,18 @@ packages: tslib: 2.6.2 dev: false + /@syndicateio/syndicate-node@0.0.449: + resolution: {integrity: sha512-pORxSFqNqxwt9lUUbuAjjtE3AzWaKlOCiNxmLOCF8ljAN2VjOjkAWXIa7mXpBzDF2KrR+PKT3VsKMlIRYgMb5w==} + dependencies: + '@types/url-join': 4.0.1 + '@ungap/url-search-params': 0.2.2 + axios: 0.27.2 + js-base64: 3.7.2 + url-join: 4.0.1 + transitivePeerDependencies: + - debug + dev: false + /@szmarczak/http-timer@4.0.6: resolution: {integrity: sha512-4BAffykYOgO+5nzBWYwE3W90sBgLJoUPRWWcL8wlyiM8IB8ipJz3UMJ9KXQd1RKQXpKp8Tutn80HZtWsu2u76w==} engines: {node: '>=10'} @@ -5206,6 +5221,10 @@ packages: resolution: {integrity: sha512-dqId9J8K/vGi5Zr7oo212BGii5m3q5Hxlkwy3WpYuKPklmBEvsbMYYyLxAQpSffdLl/gdW0XUpKWFvYmyoWCoQ==} dev: false + /@types/url-join@4.0.1: + resolution: {integrity: sha512-wDXw9LEEUHyV+7UWy7U315nrJGJ7p1BzaCxDpEoLr789Dk1WDVMMlf3iBfbG2F8NdWnYyFbtTxUn2ZNbm1Q4LQ==} + dev: false + /@types/ws@8.5.9: resolution: {integrity: sha512-jbdrY0a8lxfdTp/+r7Z4CkycbOFN8WX+IOchLJr3juT/xzbJ8URyTVSJ/hvNdadTgM1mnedb47n+Y31GsFnQlg==} dependencies: @@ -5216,6 +5235,10 @@ packages: resolution: {integrity: sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ==} dev: false + /@ungap/url-search-params@0.2.2: + resolution: {integrity: sha512-qQsguKXZVKdCixOHX9jqnX/K/1HekPDpGKyEcXHT+zR6EjGA7S4boSuelL4uuPv6YfhN0n8c4UxW+v/Z3gM2iw==} + dev: false + /@upstash/redis@1.24.3: resolution: {integrity: sha512-gw6d4IA1biB4eye5ESaXc0zOlVQI94aptsBvVcTghYWu1kRmOrJFoMFEDCa8p5uzluyYAOFCuY2GWLR6O4ZoIw==} dependencies: @@ -6160,6 +6183,15 @@ packages: resolution: {integrity: sha512-NmWvPnx0F1SfrQbYwOi7OeaNGokp9XhzNioJ/CSBs8Qa4vxug81mhJEAVZwxXuBmYB5KDRfMq/F3RR0BIU7sWg==} dev: false + /axios@0.27.2: + resolution: {integrity: sha512-t+yRIyySRTp/wua5xEr+z1q60QmLq8ABsS5O9Me1AsE5dfKqgnCFzwiCZZ/cGNd1lq4/7akDWMxdhVlucjmnOQ==} + dependencies: + follow-redirects: 1.15.5 + form-data: 4.0.0 + transitivePeerDependencies: + - debug + dev: false + /axios@1.6.7: resolution: {integrity: sha512-/hDJGff6/c7u0hDkvkGxR/oy6CbCs8ziCsC7SqmhjfozqiJGc8Z11wrv9z9lYfY4K8l+H9TpjcMDX0xOZmx+RA==} dependencies: @@ -9721,6 +9753,10 @@ packages: engines: {node: '>=10'} dev: false + /js-base64@3.7.2: + resolution: {integrity: sha512-NnRs6dsyqUXejqk/yv2aiXlAvOs56sLkX6nUdeaNezI5LFFLlsZjOThmwnrcwh5ZZRwZlCMnVAY3CvhIhoVEKQ==} + dev: false + /js-cookie@2.2.1: resolution: {integrity: sha512-HvdH2LzI/EAZcUwA8+0nKNtWHqS+ZmijLA30RwZA0bo7ToCckjK5MkGhjED9KoRcXO6BaGI3I9UIzSA1FKFPOQ==} dev: false @@ -14217,6 +14253,10 @@ packages: punycode: 2.3.1 dev: false + /url-join@4.0.1: + resolution: {integrity: sha512-jk1+QP6ZJqyOiuEI9AEWQfju/nB2Pw466kbA0LEZljHwKeMgd9WrAEgEGxjPDD2+TNbbb37rTyhEfrCXfuKXnA==} + dev: false + /url-set-query@1.0.0: resolution: {integrity: sha512-3AChu4NiXquPfeckE5R5cGdiHCMWJx1dwCWOmWIL4KHAziJNOFIYJlpGFeKDvwLPHovZRCxK3cYlwzqI9Vp+Gg==} dev: false From fcb1c1131b18fe74e4b7faedb73cc1af17429a19 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Wed, 27 Mar 2024 07:41:53 -0500 Subject: [PATCH 02/18] second pass --- apps/site/.gitignore | 1 + apps/site/app/api/post/route.ts | 100 +++++++++++------------ apps/site/app/api/postBatch/route.ts | 105 +++++++++++-------------- apps/site/app/api/registerFor/route.ts | 98 +++++++++++------------ apps/site/config/syndicateClient.ts | 20 ++--- apps/site/lib/api.ts | 30 +++++++ 6 files changed, 176 insertions(+), 178 deletions(-) diff --git a/apps/site/.gitignore b/apps/site/.gitignore index 2b6827e8..5743d4af 100644 --- a/apps/site/.gitignore +++ b/apps/site/.gitignore @@ -27,6 +27,7 @@ yarn-error.log* # local env files .env*.local .env +.env.* # vercel .vercel diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index 33441048..b872e2a1 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -5,37 +5,7 @@ import type { NextRequest } from 'next/server' import { addresses, postGatewayABI } from 'scrypt' import type { Hex } from 'viem' import { syndicate } from '@/config/syndicateClient' - -interface TransactionAttempt { - block: number - blockCreatedAt: string - chainId: number - createdAt: string - hash: string - nonce: number - reverted: boolean - signedTxn: string - status: string - transactionId: string - updatedAt: string - walletAddress: string -} - -interface SyndicateApiResponse { - chainId: number - contractAddress: string - createdAt: string - data: string - decodedData: object - functionSignature: string - invalid: boolean - projectId: string - transactionAttempts: TransactionAttempt[] - transactionId: string - updatedAt: string - value: string -} - +import { SyndicateApiResponse } from 'lib/api' export async function POST(req: NextRequest) { const post = await req.json() @@ -52,45 +22,63 @@ export async function POST(req: NextRequest) { // speed: 'fast', // }) - const postGateway = new ethers.Contract( - addresses.postGateway.nova, - postGatewayABI) + // const postGateway = new ethers.Contract( + // addresses.postGateway.nova, + // postGatewayABI, + // ) + + const postTx = await syndicate.transact.sendTransaction({ + projectId: 'a8349c10-aafd-4785-95f3-bbada9784910', + contractAddress: '0x423a602F5e551A25b28eb33eB56B961590aD5290', + chainId: 42070, + functionSignature: 'post()', + args: post, + }) - const postTx = await syndicate.transact.sendTransaction({ - projectId: 'a8349c10-aafd-4785-95f3-bbada9784910', - contractAddress: '0x423a602F5e551A25b28eb33eB56B961590aD5290', - chainId: 42070, - functionSignature: 'post()', - args: post - }) - // const tx = await postGateway.post(post) // await novaPubClient.waitForTransactionReceipt({ // hash: tx.hash as Hex, // }) - const projectId = process.env.SYNDICATE_PROJECT_ID + const projectId = process.env.SYNDICATE_PROJECT_ID_POSTGATEWAY if (!projectId) { - throw new Error("SYNDICATE_PROJECT_ID is not defined in environment variables.") + throw new Error( + 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', + ) } - const options = { method: 'GET', headers: { Authorization: 'Bearer ' } }; + const options = { + method: 'GET', + headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}` }, + } - const txResponse: SyndicateApiResponse = await fetch(`https://api.syndicate.io/wallet/project/${projectId}/request/${postTx.transactionId}`, options) - .then(response => response.json()) - .catch(err => console.error(err)) + const txResponse: SyndicateApiResponse = await fetch( + `https://api.syndicate.io/wallet/project/${projectId}/request/${postTx.transactionId}`, + options, + ) + .then((response) => response.json()) + .catch((err) => console.error(err)) if (!txResponse || !txResponse.transactionAttempts.length) { - throw new Error("Transaction attempt data not found.") + throw new Error('Transaction attempt data not found.') } - - const txHash = txResponse.transactionAttempts[0].hash - - return new Response(JSON.stringify({ success: true, hash: txHash }), { - status: 200, - headers: { 'Content-Type': 'application/json' }, - }) + let successfulTxHash = null + for (const tx of txResponse.transactionAttempts) { + if (tx.status === "SUCCESS" && !tx.reverted) { + successfulTxHash = tx.hash + break + } + } + + if (!successfulTxHash) { + throw new Error('No successful transaction attempt found.') + } + + return new Response(JSON.stringify({ success: true, hash: successfulTxHash }), { + status: 200, + headers: { 'Content-Type': 'application/json' }, + }) } catch (error) { let errorMessage = 'Unknown error' let statusCode = 500 diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index 25f476fb..d6f90ca5 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -1,40 +1,11 @@ -import { novaPubClient } from "@/config/publicClient" -import { Defender } from "@openzeppelin/defender-sdk" -import { ethers } from "ethers" -import type { NextRequest } from "next/server" -import { addresses, postGatewayABI } from "scrypt" -import type { Hex } from "viem" -import { syndicate } from "@/config/syndicateClient" - -interface TransactionAttempt { - block: number - blockCreatedAt: string - chainId: number - createdAt: string - hash: string - nonce: number - reverted: boolean - signedTxn: string - status: string - transactionId: string - updatedAt: string - walletAddress: string -} - -interface SyndicateApiResponse { - chainId: number - contractAddress: string - createdAt: string - data: string - decodedData: object - functionSignature: string - invalid: boolean - projectId: string - transactionAttempts: TransactionAttempt[] - transactionId: string - updatedAt: string - value: string -} +import { novaPubClient } from '@/config/publicClient' +import { Defender } from '@openzeppelin/defender-sdk' +import { ethers } from 'ethers' +import type { NextRequest } from 'next/server' +import { addresses, postGatewayABI } from 'scrypt' +import type { Hex } from 'viem' +import { syndicate } from '@/config/syndicateClient' +import { SyndicateApiResponse } from 'lib/api' export async function POST(req: NextRequest) { const postsArray = await req.json() @@ -52,29 +23,37 @@ export async function POST(req: NextRequest) { // speed: 'fast', // }) - const postGateway = new ethers.Contract( - addresses.postGateway.nova, - postGatewayABI - ) + // const postGateway = new ethers.Contract( + // addresses.postGateway.nova, + // postGatewayABI, + // ) - const projectId = process.env.SYNDICATE_PROJECT_ID + const projectId = process.env.SYNDICATE_PROJECT_ID_POSTGATEWAY if (!projectId) { - throw new Error("SYNDICATE_PROJECT_ID is not defined in environment variables.") + throw new Error( + 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', + ) } const postBatchTx = await syndicate.transact.sendTransaction({ projectId: projectId, contractAddress: addresses.postGateway.nova, chainId: 42170, functionSignature: - "postBatch((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig)[] posts)", - args: postsArray + 'postBatch((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig)[] posts)', + args: postsArray, }) - const options = { method: 'GET', headers: { Authorization: 'Bearer ' } }; + const options = { + method: 'GET', + headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}` }, + } - const txResponse: SyndicateApiResponse = await fetch(`https://api.syndicate.io/wallet/project/${projectId}/request/${postBatchTx.transactionId}`, options) - .then(response => response.json()) - .catch(err => console.error(err)) + const txResponse: SyndicateApiResponse = await fetch( + `https://api.syndicate.io/wallet/project/${projectId}/request/${postBatchTx.transactionId}`, + options, + ) + .then((response) => response.json()) + .catch((err) => console.error(err)) // const tx = await postGateway.postBatch(postsArray) // await novaPubClient.waitForTransactionReceipt({ @@ -82,32 +61,40 @@ export async function POST(req: NextRequest) { // }) if (!txResponse || !txResponse.transactionAttempts.length) { - throw new Error("Transaction attempt data not found.") + throw new Error('Transaction attempt data not found.') } - - const txHash = txResponse.transactionAttempts[0].hash - - return new Response(JSON.stringify({ success: true, hash: txHash}), { + let successfulTxHash = null + for (const tx of txResponse.transactionAttempts) { + if (tx.status === "SUCCESS" && !tx.reverted) { + successfulTxHash = tx.hash + break + } + } + if (!successfulTxHash) { + throw new Error('No successful transaction attempt found.') + } + + return new Response(JSON.stringify({ success: true, hash: successfulTxHash }), { status: 200, - headers: { "Content-Type": "application/json" }, + headers: { 'Content-Type': 'application/json' }, }) } catch (error) { - let errorMessage = "Unknown error" + let errorMessage = 'Unknown error' let statusCode = 500 if (error instanceof Error) { errorMessage = error.message statusCode = // biome-ignore lint: `status` is not part of the standard Error interface - typeof (error as any).status === "number" ? (error as any).status : 500 + typeof (error as any).status === 'number' ? (error as any).status : 500 } return new Response( JSON.stringify({ success: false, hash: null, error: errorMessage }), { status: statusCode, - headers: { "Content-Type": "application/json" }, - } + headers: { 'Content-Type': 'application/json' }, + }, ) } } diff --git a/apps/site/app/api/registerFor/route.ts b/apps/site/app/api/registerFor/route.ts index ef3cac19..cd334b73 100644 --- a/apps/site/app/api/registerFor/route.ts +++ b/apps/site/app/api/registerFor/route.ts @@ -5,37 +5,7 @@ import type { NextRequest } from 'next/server' import { addresses, idRegistryABI } from 'scrypt' import { type Hex, decodeAbiParameters } from 'viem' import { syndicate } from '@/config/syndicateClient' - - -interface SyndicateApiResponse { - chainId: number - contractAddress: string - createdAt: string - data: string - decodedData: object - functionSignature: string - invalid: boolean - projectId: string - transactionAttempts: TransactionAttempt[] - transactionId: string - updatedAt: string - value: string -} - -interface TransactionAttempt { - block: number - blockCreatedAt: string - chainId: number - createdAt: string - hash: string - nonce: number - reverted: boolean - signedTxn: string - status: string - transactionId: string - updatedAt: string - walletAddress: string -} +import { SyndicateApiResponse } from 'lib/api' export async function POST(req: NextRequest) { const user = await req.json() @@ -51,7 +21,6 @@ export async function POST(req: NextRequest) { // relayerApiSecret: process.env.IDREGISTRY_SECRET_UNO, // } - try { // const defenderClient = new Defender(credentials) // const provider = defenderClient.relaySigner.getProvider() @@ -61,8 +30,8 @@ export async function POST(req: NextRequest) { const idRegistry = new ethers.Contract( addresses.idRegistry.optimism, - idRegistryABI, - ) + idRegistryABI, + ) // const registerTxn = await idRegistry.registerFor( // to, @@ -71,17 +40,20 @@ export async function POST(req: NextRequest) { // sig, // ) - const projectId = process.env.SYNDICATE_PROJECT_ID - if (!projectId) { - throw new Error("SYNDICATE_PROJECT_ID is not defined in environment variables.") - } + const projectId = process.env.SYNDICATE_PROJECT_ID_IDREGISTRY + if (!projectId) { + throw new Error( + 'SYNDICATE_PROJECT_ID is not defined in environment variables.', + ) + } const registerTx = await syndicate.transact.sendTransaction({ projectId: projectId, contractAddress: addresses.idRegistry.optimism, - chainId: 420, - functionSignature: 'registerFor(address to, address recovery, uint256 deadline, bytes sig)', - args: userWithoutUsername + chainId: 420, + functionSignature: + 'registerFor(address to, address recovery, uint256 deadline, bytes sig)', + args: userWithoutUsername, }) // const txnReceipt = await optimismPubClient.waitForTransactionReceipt({ @@ -99,17 +71,31 @@ export async function POST(req: NextRequest) { // console.log('rid: ', rid) console.log('transaction receipt: ', registerTx) - const options = { method: 'GET', headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}` } } - const txResponse: SyndicateApiResponse = await fetch(`https://api.syndicate.io/wallet/project/${projectId}/request/${registerTx.transactionId}`, options) - .then(response => response.json()) + const options = { + method: 'GET', + headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}` }, + } + const txResponse: SyndicateApiResponse = await fetch( + `https://api.syndicate.io/wallet/project/${projectId}/request/${registerTx.transactionId}`, + options, + ).then((response) => response.json()) if (!txResponse || !txResponse.transactionAttempts.length) { - throw new Error("Transaction attempt data not found.") + throw new Error('Transaction attempt data not found.') } - - const txHash = txResponse.transactionAttempts[0].hash - - return new Response(JSON.stringify({ success: true, hash: txHash }), { + let successfulTxHash = null + for (const tx of txResponse.transactionAttempts) { + if (tx.status === "SUCCESS" && !tx.reverted) { + successfulTxHash = tx.hash + break + } + } + + if (!successfulTxHash) { + throw new Error('No successful transaction attempt found.') + } + + return new Response(JSON.stringify({ success: true, hash: successfulTxHash }), { status: 200, headers: { 'Content-Type': 'application/json' }, }) @@ -120,12 +106,16 @@ export async function POST(req: NextRequest) { if (error instanceof Error) { errorMessage = error.message - statusCode = typeof (error as any).status === 'number' ? (error as any).status : 500 + statusCode = + typeof (error as any).status === 'number' ? (error as any).status : 500 } - return new Response(JSON.stringify({ success: false, error: errorMessage }), { - status: statusCode, - headers: { 'Content-Type': 'application/json' }, - }) + return new Response( + JSON.stringify({ success: false, error: errorMessage }), + { + status: statusCode, + headers: { 'Content-Type': 'application/json' }, + }, + ) } } diff --git a/apps/site/config/syndicateClient.ts b/apps/site/config/syndicateClient.ts index 7e8ab24f..226fed72 100644 --- a/apps/site/config/syndicateClient.ts +++ b/apps/site/config/syndicateClient.ts @@ -1,11 +1,13 @@ -import { SyndicateClient } from "@syndicateio/syndicate-node"; +import { SyndicateClient } from '@syndicateio/syndicate-node' export const syndicate = new SyndicateClient({ - token: () => { - const apiKey = process.env.SYNDICATE_API_KEY - if (typeof apiKey === "undefined") { - throw new Error("SYNDICATE_API_KEY is not defined in environment variables.") - } - return apiKey; - }, - }); \ No newline at end of file + token: () => { + const apiKey = process.env.SYNDICATE_API_KEY + if (typeof apiKey === 'undefined') { + throw new Error( + 'SYNDICATE_API_KEY is not defined in environment variables.', + ) + } + return apiKey + }, +}) diff --git a/apps/site/lib/api.ts b/apps/site/lib/api.ts index 3e78e61a..1170112c 100644 --- a/apps/site/lib/api.ts +++ b/apps/site/lib/api.ts @@ -21,6 +21,36 @@ type User = { sig: string } +export interface TransactionAttempt { + block: number + blockCreatedAt: string + chainId: number + createdAt: string + hash: string + nonce: number + reverted: boolean + signedTxn: string + status: string + transactionId: string + updatedAt: string + walletAddress: string +} + +export interface SyndicateApiResponse { + chainId: number + contractAddress: string + createdAt: string + data: string + decodedData: object + functionSignature: string + invalid: boolean + projectId: string + transactionAttempts: TransactionAttempt[] + transactionId: string + updatedAt: string + value: string +} + /* API ROUTES */ // This is in to help with serialization of bigints during json stringify From 55a14b28b3b7d16ffd2f512ccaf5a517f7786cc2 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Wed, 27 Mar 2024 07:58:01 -0500 Subject: [PATCH 03/18] added post function sig, formatted and lint --- apps/site/app/api/post/route.ts | 40 ++++++++++++++------------ apps/site/app/api/postBatch/route.ts | 19 ++++++------ apps/site/app/api/registerFor/route.ts | 22 ++++++++------ 3 files changed, 46 insertions(+), 35 deletions(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index b872e2a1..5b89027b 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -5,7 +5,7 @@ import type { NextRequest } from 'next/server' import { addresses, postGatewayABI } from 'scrypt' import type { Hex } from 'viem' import { syndicate } from '@/config/syndicateClient' -import { SyndicateApiResponse } from 'lib/api' +import type { SyndicateApiResponse } from 'lib/api' export async function POST(req: NextRequest) { const post = await req.json() @@ -31,7 +31,8 @@ export async function POST(req: NextRequest) { projectId: 'a8349c10-aafd-4785-95f3-bbada9784910', contractAddress: '0x423a602F5e551A25b28eb33eB56B961590aD5290', chainId: 42070, - functionSignature: 'post()', + functionSignature: + 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig))', args: post, }) @@ -60,25 +61,28 @@ export async function POST(req: NextRequest) { .then((response) => response.json()) .catch((err) => console.error(err)) - if (!txResponse || !txResponse.transactionAttempts.length) { - throw new Error('Transaction attempt data not found.') - } - let successfulTxHash = null - for (const tx of txResponse.transactionAttempts) { - if (tx.status === "SUCCESS" && !tx.reverted) { - successfulTxHash = tx.hash - break - } - } - - if (!successfulTxHash) { - throw new Error('No successful transaction attempt found.') + if (!txResponse || !txResponse.transactionAttempts.length) { + throw new Error('Transaction attempt data not found.') + } + let successfulTxHash = null + for (const tx of txResponse.transactionAttempts) { + if (tx.status === 'SUCCESS' && !tx.reverted) { + successfulTxHash = tx.hash + break } - - return new Response(JSON.stringify({ success: true, hash: successfulTxHash }), { + } + + if (!successfulTxHash) { + throw new Error('No successful transaction attempt found.') + } + + return new Response( + JSON.stringify({ success: true, hash: successfulTxHash }), + { status: 200, headers: { 'Content-Type': 'application/json' }, - }) + }, + ) } catch (error) { let errorMessage = 'Unknown error' let statusCode = 500 diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index d6f90ca5..0daf6e03 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -5,7 +5,7 @@ import type { NextRequest } from 'next/server' import { addresses, postGatewayABI } from 'scrypt' import type { Hex } from 'viem' import { syndicate } from '@/config/syndicateClient' -import { SyndicateApiResponse } from 'lib/api' +import type { SyndicateApiResponse } from 'lib/api' export async function POST(req: NextRequest) { const postsArray = await req.json() @@ -65,19 +65,22 @@ export async function POST(req: NextRequest) { } let successfulTxHash = null for (const tx of txResponse.transactionAttempts) { - if (tx.status === "SUCCESS" && !tx.reverted) { + if (tx.status === 'SUCCESS' && !tx.reverted) { successfulTxHash = tx.hash - break + break } } if (!successfulTxHash) { throw new Error('No successful transaction attempt found.') } - - return new Response(JSON.stringify({ success: true, hash: successfulTxHash }), { - status: 200, - headers: { 'Content-Type': 'application/json' }, - }) + + return new Response( + JSON.stringify({ success: true, hash: successfulTxHash }), + { + status: 200, + headers: { 'Content-Type': 'application/json' }, + }, + ) } catch (error) { let errorMessage = 'Unknown error' let statusCode = 500 diff --git a/apps/site/app/api/registerFor/route.ts b/apps/site/app/api/registerFor/route.ts index cd334b73..ffab4bc5 100644 --- a/apps/site/app/api/registerFor/route.ts +++ b/apps/site/app/api/registerFor/route.ts @@ -5,7 +5,7 @@ import type { NextRequest } from 'next/server' import { addresses, idRegistryABI } from 'scrypt' import { type Hex, decodeAbiParameters } from 'viem' import { syndicate } from '@/config/syndicateClient' -import { SyndicateApiResponse } from 'lib/api' +import type { SyndicateApiResponse } from 'lib/api' export async function POST(req: NextRequest) { const user = await req.json() @@ -85,20 +85,23 @@ export async function POST(req: NextRequest) { } let successfulTxHash = null for (const tx of txResponse.transactionAttempts) { - if (tx.status === "SUCCESS" && !tx.reverted) { + if (tx.status === 'SUCCESS' && !tx.reverted) { successfulTxHash = tx.hash - break + break } } - + if (!successfulTxHash) { throw new Error('No successful transaction attempt found.') } - - return new Response(JSON.stringify({ success: true, hash: successfulTxHash }), { - status: 200, - headers: { 'Content-Type': 'application/json' }, - }) + + return new Response( + JSON.stringify({ success: true, hash: successfulTxHash }), + { + status: 200, + headers: { 'Content-Type': 'application/json' }, + }, + ) } catch (error) { console.error(error) let errorMessage = 'Unknown error' @@ -107,6 +110,7 @@ export async function POST(req: NextRequest) { if (error instanceof Error) { errorMessage = error.message statusCode = + // biome-ignore lint: `status` is not part of the standard Error interface typeof (error as any).status === 'number' ? (error as any).status : 500 } From 8a432982cd753e271cfea6be5a8266237b9179ff Mon Sep 17 00:00:00 2001 From: jawndiego Date: Wed, 27 Mar 2024 12:06:24 -0500 Subject: [PATCH 04/18] syndicate third pass --- apps/delta/ponder.config.ts | 2 +- apps/site/app/api/post/route.ts | 6 +++--- apps/site/app/api/postBatch/route.ts | 24 ++++++++++++++++-------- apps/site/app/api/registerFor/route.ts | 4 ++-- 4 files changed, 22 insertions(+), 14 deletions(-) diff --git a/apps/delta/ponder.config.ts b/apps/delta/ponder.config.ts index 554a93c3..b9b585a9 100644 --- a/apps/delta/ponder.config.ts +++ b/apps/delta/ponder.config.ts @@ -1,6 +1,6 @@ import { createConfig } from '@ponder/core' import { addresses, idRegistryABI, postGatewayABI } from 'scrypt' -import { http } from 'viem' +import { Hex, http } from 'viem' export default createConfig({ networks: { diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index 5b89027b..1968ed86 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -33,7 +33,7 @@ export async function POST(req: NextRequest) { chainId: 42070, functionSignature: 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig))', - args: post, + args: {post}, }) // const tx = await postGateway.post(post) @@ -51,7 +51,7 @@ export async function POST(req: NextRequest) { const options = { method: 'GET', - headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}` }, + headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}`}, } const txResponse: SyndicateApiResponse = await fetch( @@ -66,7 +66,7 @@ export async function POST(req: NextRequest) { } let successfulTxHash = null for (const tx of txResponse.transactionAttempts) { - if (tx.status === 'SUCCESS' && !tx.reverted) { + if (tx.status === 'CONFIRMED' && !tx.reverted) { successfulTxHash = tx.hash break } diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index 0daf6e03..04fe8bc7 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -5,11 +5,10 @@ import type { NextRequest } from 'next/server' import { addresses, postGatewayABI } from 'scrypt' import type { Hex } from 'viem' import { syndicate } from '@/config/syndicateClient' -import type { SyndicateApiResponse } from 'lib/api' +import type { SyndicateApiResponse, TransactionAttempt } from 'lib/api' export async function POST(req: NextRequest) { const postsArray = await req.json() - console.log({ postsArray }) // const credentials = { // relayerApiKey: process.env.NONCE_API_UNO, @@ -29,19 +28,23 @@ export async function POST(req: NextRequest) { // ) const projectId = process.env.SYNDICATE_PROJECT_ID_POSTGATEWAY + if (!projectId) { throw new Error( 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', ) } + const postBatchTx = await syndicate.transact.sendTransaction({ projectId: projectId, contractAddress: addresses.postGateway.nova, chainId: 42170, functionSignature: 'postBatch((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig)[] posts)', - args: postsArray, - }) + args: { + posts: postsArray, + }, + }) const options = { method: 'GET', @@ -55,18 +58,23 @@ export async function POST(req: NextRequest) { .then((response) => response.json()) .catch((err) => console.error(err)) + console.log({txResponse}) + console.log("transaction attempt", txResponse.transactionAttempts) + // const tx = await postGateway.postBatch(postsArray) // await novaPubClient.waitForTransactionReceipt({ // hash: tx.hash as Hex, // }) - if (!txResponse || !txResponse.transactionAttempts.length) { - throw new Error('Transaction attempt data not found.') - } + // if (!txResponse || !txResponse.transactionAttempts.length) { + // throw new Error('Transaction attempt data not found.') + // } + let successfulTxHash = null for (const tx of txResponse.transactionAttempts) { - if (tx.status === 'SUCCESS' && !tx.reverted) { + if (tx.status === 'CONFIRMED' && !tx.reverted) { successfulTxHash = tx.hash + console.log("successfulTxHash", successfulTxHash) break } } diff --git a/apps/site/app/api/registerFor/route.ts b/apps/site/app/api/registerFor/route.ts index ffab4bc5..bcc3f108 100644 --- a/apps/site/app/api/registerFor/route.ts +++ b/apps/site/app/api/registerFor/route.ts @@ -53,7 +53,7 @@ export async function POST(req: NextRequest) { chainId: 420, functionSignature: 'registerFor(address to, address recovery, uint256 deadline, bytes sig)', - args: userWithoutUsername, + args: {userWithoutUsername}, }) // const txnReceipt = await optimismPubClient.waitForTransactionReceipt({ @@ -85,7 +85,7 @@ export async function POST(req: NextRequest) { } let successfulTxHash = null for (const tx of txResponse.transactionAttempts) { - if (tx.status === 'SUCCESS' && !tx.reverted) { + if (tx.status === 'CONFIRMED' && !tx.reverted) { successfulTxHash = tx.hash break } From 13d200a1728bcea6fffc3ed3b92b10b7b1f19df3 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Wed, 27 Mar 2024 12:11:22 -0500 Subject: [PATCH 05/18] format and lint --- apps/site/app/api/post/route.ts | 4 ++-- apps/site/app/api/postBatch/route.ts | 14 +++++++------- apps/site/app/api/registerFor/route.ts | 2 +- 3 files changed, 10 insertions(+), 10 deletions(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index 1968ed86..249c98aa 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -33,7 +33,7 @@ export async function POST(req: NextRequest) { chainId: 42070, functionSignature: 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig))', - args: {post}, + args: { post }, }) // const tx = await postGateway.post(post) @@ -51,7 +51,7 @@ export async function POST(req: NextRequest) { const options = { method: 'GET', - headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}`}, + headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}` }, } const txResponse: SyndicateApiResponse = await fetch( diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index 04fe8bc7..2bb768fe 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -41,10 +41,10 @@ export async function POST(req: NextRequest) { chainId: 42170, functionSignature: 'postBatch((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig)[] posts)', - args: { - posts: postsArray, - }, - }) + args: { + posts: postsArray, + }, + }) const options = { method: 'GET', @@ -58,8 +58,8 @@ export async function POST(req: NextRequest) { .then((response) => response.json()) .catch((err) => console.error(err)) - console.log({txResponse}) - console.log("transaction attempt", txResponse.transactionAttempts) + console.log({ txResponse }) + console.log('transaction attempt', txResponse.transactionAttempts) // const tx = await postGateway.postBatch(postsArray) // await novaPubClient.waitForTransactionReceipt({ @@ -74,7 +74,7 @@ export async function POST(req: NextRequest) { for (const tx of txResponse.transactionAttempts) { if (tx.status === 'CONFIRMED' && !tx.reverted) { successfulTxHash = tx.hash - console.log("successfulTxHash", successfulTxHash) + console.log('successfulTxHash', successfulTxHash) break } } diff --git a/apps/site/app/api/registerFor/route.ts b/apps/site/app/api/registerFor/route.ts index bcc3f108..248955d6 100644 --- a/apps/site/app/api/registerFor/route.ts +++ b/apps/site/app/api/registerFor/route.ts @@ -53,7 +53,7 @@ export async function POST(req: NextRequest) { chainId: 420, functionSignature: 'registerFor(address to, address recovery, uint256 deadline, bytes sig)', - args: {userWithoutUsername}, + args: { userWithoutUsername }, }) // const txnReceipt = await optimismPubClient.waitForTransactionReceipt({ From 0883ee31e8580cdf3f9992ce0f5e172f8b1dd694 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Thu, 28 Mar 2024 18:05:43 -0500 Subject: [PATCH 06/18] postBatch working, post in progress, register not tested --- apps/site/app/api/post/route.ts | 103 ++++++++++++++----------- apps/site/app/api/postBatch/route.ts | 48 ++++-------- apps/site/app/api/registerFor/route.ts | 58 ++++++-------- apps/site/lib/api.ts | 55 +++++++++++++ 4 files changed, 151 insertions(+), 113 deletions(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index 249c98aa..a4adcc8f 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -1,14 +1,14 @@ -import { novaPubClient } from '@/config/publicClient' -import { Defender } from '@openzeppelin/defender-sdk' -import { ethers } from 'ethers' import type { NextRequest } from 'next/server' -import { addresses, postGatewayABI } from 'scrypt' -import type { Hex } from 'viem' import { syndicate } from '@/config/syndicateClient' -import type { SyndicateApiResponse } from 'lib/api' +import { addresses } from 'scrypt' +import { waitUntilTx } from '@/lib' + export async function POST(req: NextRequest) { const post = await req.json() + console.log("POSTY", post) + + /* DEFENDER CODE */ // const credentials = { // relayerApiKey: process.env.NONCE_API_UNO, @@ -16,6 +16,9 @@ export async function POST(req: NextRequest) { // } try { + + /* DEFENDER CODE */ + // const defenderClient = new Defender(credentials) // const provider = defenderClient.relaySigner.getProvider() // const signer = defenderClient.relaySigner.getSigner(provider, { @@ -27,54 +30,68 @@ export async function POST(req: NextRequest) { // postGatewayABI, // ) - const postTx = await syndicate.transact.sendTransaction({ - projectId: 'a8349c10-aafd-4785-95f3-bbada9784910', - contractAddress: '0x423a602F5e551A25b28eb33eB56B961590aD5290', - chainId: 42070, - functionSignature: - 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig))', - args: { post }, - }) - - // const tx = await postGateway.post(post) - - // await novaPubClient.waitForTransactionReceipt({ - // hash: tx.hash as Hex, - // }) const projectId = process.env.SYNDICATE_PROJECT_ID_POSTGATEWAY + if (!projectId) { throw new Error( 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', ) } - const options = { - method: 'GET', - headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}` }, - } + // const args = { + // signer: post.signer, // Assuming this is correctly formatted as an address string + // message: { + // // Convert string numeric values to actual numbers. + // // Ensure these conversions maintain the integrity of the values. + // rid: parseInt(post.message.rid, 10), + // timestamp: parseInt(post.message.timestamp, 10), + // msgType: post.message.msgType, // Assuming this is already the correct type + // msgBody: post.message.msgBody, // Assuming this is correctly formatted as bytes + // }, + // hashType: post.hashType, // Assuming this is already the correct type + // hash: post.hash, // Assuming this is correctly formatted as bytes32 + // sigType: post.sigType, // Assuming this is already the correct type + // sig: post.sig // Assuming this is correctly formatted as bytes + // }; - const txResponse: SyndicateApiResponse = await fetch( - `https://api.syndicate.io/wallet/project/${projectId}/request/${postTx.transactionId}`, - options, + const postTx = await syndicate.transact.sendTransaction({ + projectId: projectId, + contractAddress: addresses.postGateway.nova, + chainId: 42170, + functionSignature:'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig))', + args: { + signer: post.signer, + message: { + rid: post.message.rid, + timestamp: post.message.timestamp, + msgType: post.message.msgType, + msgBody: post.message.msgBody, + }, + hashType: post.hashType, + hash: post.hash, + sigType: post.sigType, + sig: post.sig, + }, + }, ) - .then((response) => response.json()) - .catch((err) => console.error(err)) - if (!txResponse || !txResponse.transactionAttempts.length) { - throw new Error('Transaction attempt data not found.') - } - let successfulTxHash = null - for (const tx of txResponse.transactionAttempts) { - if (tx.status === 'CONFIRMED' && !tx.reverted) { - successfulTxHash = tx.hash - break - } - } + console.log({postTx}) - if (!successfulTxHash) { - throw new Error('No successful transaction attempt found.') - } + // const tx = await postGateway.post(post) + + // await novaPubClient.waitForTransactionReceipt({ + // hash: tx.hash as Hex, + // }) + + + // Use the waitUntilTx function to wait for the transaction to be processed + const successfulTxHash = await waitUntilTx({ + projectID: projectId, + txID: postTx.transactionId, + }) + + console.log({successfulTxHash}) return new Response( JSON.stringify({ success: true, hash: successfulTxHash }), @@ -102,4 +119,4 @@ export async function POST(req: NextRequest) { }, ) } -} +} \ No newline at end of file diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index 2bb768fe..edc0b801 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -1,21 +1,22 @@ -import { novaPubClient } from '@/config/publicClient' -import { Defender } from '@openzeppelin/defender-sdk' -import { ethers } from 'ethers' import type { NextRequest } from 'next/server' -import { addresses, postGatewayABI } from 'scrypt' -import type { Hex } from 'viem' +import { addresses } from 'scrypt' import { syndicate } from '@/config/syndicateClient' -import type { SyndicateApiResponse, TransactionAttempt } from 'lib/api' +import { waitUntilTx, } from '@/lib' export async function POST(req: NextRequest) { const postsArray = await req.json() + /* DEFENDER CODE */ + // const credentials = { // relayerApiKey: process.env.NONCE_API_UNO, // relayerApiSecret: process.env.NONCE_SECRET_UNO, // } try { + + /* DEFENDER CODE */ + // const defenderClient = new Defender(credentials) // const provider = defenderClient.relaySigner.getProvider() // const signer = defenderClient.relaySigner.getSigner(provider, { @@ -46,42 +47,19 @@ export async function POST(req: NextRequest) { }, }) - const options = { - method: 'GET', - headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}` }, - } - - const txResponse: SyndicateApiResponse = await fetch( - `https://api.syndicate.io/wallet/project/${projectId}/request/${postBatchTx.transactionId}`, - options, - ) - .then((response) => response.json()) - .catch((err) => console.error(err)) + // Use the waitUntilTx function to wait for the transaction to be processed + const successfulTxHash = await waitUntilTx({ + projectID: projectId, + txID: postBatchTx.transactionId, + }) - console.log({ txResponse }) - console.log('transaction attempt', txResponse.transactionAttempts) + /* DEFENDER CODE */ // const tx = await postGateway.postBatch(postsArray) // await novaPubClient.waitForTransactionReceipt({ // hash: tx.hash as Hex, // }) - // if (!txResponse || !txResponse.transactionAttempts.length) { - // throw new Error('Transaction attempt data not found.') - // } - - let successfulTxHash = null - for (const tx of txResponse.transactionAttempts) { - if (tx.status === 'CONFIRMED' && !tx.reverted) { - successfulTxHash = tx.hash - console.log('successfulTxHash', successfulTxHash) - break - } - } - if (!successfulTxHash) { - throw new Error('No successful transaction attempt found.') - } - return new Response( JSON.stringify({ success: true, hash: successfulTxHash }), { diff --git a/apps/site/app/api/registerFor/route.ts b/apps/site/app/api/registerFor/route.ts index 248955d6..792ea3b4 100644 --- a/apps/site/app/api/registerFor/route.ts +++ b/apps/site/app/api/registerFor/route.ts @@ -1,11 +1,7 @@ -import { optimismPubClient } from '@/config/publicClient' -import { Defender } from '@openzeppelin/defender-sdk' -import { ethers } from 'ethers' import type { NextRequest } from 'next/server' -import { addresses, idRegistryABI } from 'scrypt' -import { type Hex, decodeAbiParameters } from 'viem' +import { addresses } from 'scrypt' import { syndicate } from '@/config/syndicateClient' -import type { SyndicateApiResponse } from 'lib/api' +import { waitUntilTx, } from '@/lib' export async function POST(req: NextRequest) { const user = await req.json() @@ -16,22 +12,29 @@ export async function POST(req: NextRequest) { console.log({ userWithoutUsername }) + /* DEFENDER CODE */ + // const credentials = { // relayerApiKey: process.env.IDREGISTRY_API_UNO, // relayerApiSecret: process.env.IDREGISTRY_SECRET_UNO, // } try { + /* DEFENDER CODE */ + // const defenderClient = new Defender(credentials) // const provider = defenderClient.relaySigner.getProvider() // const signer = defenderClient.relaySigner.getSigner(provider, { // speed: 'fast', // }) - const idRegistry = new ethers.Contract( - addresses.idRegistry.optimism, - idRegistryABI, - ) + // const idRegistry = new ethers.Contract( + // addresses.idRegistry.optimism, + // idRegistryABI, + // ) + + /* DEFENDER CODE */ + // const registerTxn = await idRegistry.registerFor( // to, @@ -56,6 +59,15 @@ export async function POST(req: NextRequest) { args: { userWithoutUsername }, }) + // Use the waitUntilTx function to wait for the transaction to be processed + const successfulTxHash = await waitUntilTx({ + projectID: projectId, + txID: registerTx.transactionId, + }) + + + /* DEFENDER CODE */ + // const txnReceipt = await optimismPubClient.waitForTransactionReceipt({ // hash: registerTxn.hash as Hex, // }) @@ -69,32 +81,8 @@ export async function POST(req: NextRequest) { // ) // console.log('rid: ', rid) - console.log('transaction receipt: ', registerTx) - - const options = { - method: 'GET', - headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}` }, - } - const txResponse: SyndicateApiResponse = await fetch( - `https://api.syndicate.io/wallet/project/${projectId}/request/${registerTx.transactionId}`, - options, - ).then((response) => response.json()) - - if (!txResponse || !txResponse.transactionAttempts.length) { - throw new Error('Transaction attempt data not found.') - } - let successfulTxHash = null - for (const tx of txResponse.transactionAttempts) { - if (tx.status === 'CONFIRMED' && !tx.reverted) { - successfulTxHash = tx.hash - break - } - } - - if (!successfulTxHash) { - throw new Error('No successful transaction attempt found.') - } + return new Response( JSON.stringify({ success: true, hash: successfulTxHash }), { diff --git a/apps/site/lib/api.ts b/apps/site/lib/api.ts index 1170112c..35e4ed0d 100644 --- a/apps/site/lib/api.ts +++ b/apps/site/lib/api.ts @@ -51,6 +51,61 @@ export interface SyndicateApiResponse { value: string } + +export interface WaitUntilTxOptions { + projectID: string + txID: string + maxAttempts?: number + every?: number +} + +export const getTransactionRequest = async ({ projectID, txID }: Pick) => { + const response = await fetch( + `https://api.syndicate.io/wallet/project/${projectID}/request/${txID}`, + { + method: 'GET', + headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}` }, + }, + ) + if (!response.ok) { + throw new Error(`Failed to get transaction request: ${response.statusText}`) + } + return response.json() +} + +export async function waitUntilTx({ + projectID, + txID, + maxAttempts = 20, + every = 1000, +}: WaitUntilTxOptions) { + let currAttempts = 0 + let transactionHash = null + + while (!transactionHash) { + await new Promise((resolve) => setTimeout(resolve, every)) + + if (currAttempts >= maxAttempts) { + throw new Error("Max attempts reached") + } + + const txAttempts = (await getTransactionRequest({ projectID, txID }))?.transactionAttempts + + console.log({txAttempts}) + + if (txAttempts && txAttempts.length > 0 && txAttempts[txAttempts.length - 1].status === 'PENDING' && !txAttempts[txAttempts.length - 1].reverted) { + transactionHash = txAttempts[txAttempts.length - 1].hash + console.log(transactionHash) + break + } + + currAttempts += 1 + } + + return transactionHash +} + + /* API ROUTES */ // This is in to help with serialization of bigints during json stringify From aecd49af36046c29436fd3fe9ac0d80ba2efc051 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Fri, 29 Mar 2024 10:38:04 -0500 Subject: [PATCH 07/18] post working --- apps/site/app/api/post/route.ts | 39 ++++++---------------------- apps/site/app/api/postBatch/route.ts | 1 + 2 files changed, 9 insertions(+), 31 deletions(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index a4adcc8f..e27f8313 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -6,7 +6,9 @@ import { waitUntilTx } from '@/lib' export async function POST(req: NextRequest) { const post = await req.json() - console.log("POSTY", post) + console.log("post", post) + + /* DEFENDER CODE */ @@ -39,42 +41,17 @@ export async function POST(req: NextRequest) { ) } - // const args = { - // signer: post.signer, // Assuming this is correctly formatted as an address string - // message: { - // // Convert string numeric values to actual numbers. - // // Ensure these conversions maintain the integrity of the values. - // rid: parseInt(post.message.rid, 10), - // timestamp: parseInt(post.message.timestamp, 10), - // msgType: post.message.msgType, // Assuming this is already the correct type - // msgBody: post.message.msgBody, // Assuming this is correctly formatted as bytes - // }, - // hashType: post.hashType, // Assuming this is already the correct type - // hash: post.hash, // Assuming this is correctly formatted as bytes32 - // sigType: post.sigType, // Assuming this is already the correct type - // sig: post.sig // Assuming this is correctly formatted as bytes - // }; + const postTx = await syndicate.transact.sendTransaction({ projectId: projectId, contractAddress: addresses.postGateway.nova, chainId: 42170, - functionSignature:'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig))', + functionSignature: 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig) post)', args: { - signer: post.signer, - message: { - rid: post.message.rid, - timestamp: post.message.timestamp, - msgType: post.message.msgType, - msgBody: post.message.msgBody, - }, - hashType: post.hashType, - hash: post.hash, - sigType: post.sigType, - sig: post.sig, - }, - }, - ) + post: post + } + }) console.log({postTx}) diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index edc0b801..71ec0ac0 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -5,6 +5,7 @@ import { waitUntilTx, } from '@/lib' export async function POST(req: NextRequest) { const postsArray = await req.json() + console.log("postArray", postsArray) /* DEFENDER CODE */ From 84f8181b38a4e04a61ac9be9593e03972048cbfa Mon Sep 17 00:00:00 2001 From: jawndiego Date: Fri, 29 Mar 2024 10:51:04 -0500 Subject: [PATCH 08/18] format and cleaned --- apps/site/app/api/post/route.ts | 50 ++---------- apps/site/app/api/postBatch/route.ts | 35 +------- apps/site/app/api/registerFor/route.ts | 108 ++++++++++--------------- apps/site/lib/api.ts | 21 +++-- 4 files changed, 66 insertions(+), 148 deletions(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index e27f8313..c5838e93 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -3,36 +3,10 @@ import { syndicate } from '@/config/syndicateClient' import { addresses } from 'scrypt' import { waitUntilTx } from '@/lib' - export async function POST(req: NextRequest) { const post = await req.json() - console.log("post", post) - - - - /* DEFENDER CODE */ - - // const credentials = { - // relayerApiKey: process.env.NONCE_API_UNO, - // relayerApiSecret: process.env.NONCE_SECRET_UNO, - // } try { - - /* DEFENDER CODE */ - - // const defenderClient = new Defender(credentials) - // const provider = defenderClient.relaySigner.getProvider() - // const signer = defenderClient.relaySigner.getSigner(provider, { - // speed: 'fast', - // }) - - // const postGateway = new ethers.Contract( - // addresses.postGateway.nova, - // postGatewayABI, - // ) - - const projectId = process.env.SYNDICATE_PROJECT_ID_POSTGATEWAY if (!projectId) { @@ -41,34 +15,26 @@ export async function POST(req: NextRequest) { ) } - - const postTx = await syndicate.transact.sendTransaction({ projectId: projectId, contractAddress: addresses.postGateway.nova, chainId: 42170, - functionSignature: 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig) post)', + functionSignature: + 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig) post)', args: { - post: post - } + post: post, + }, }) - console.log({postTx}) - - // const tx = await postGateway.post(post) - - // await novaPubClient.waitForTransactionReceipt({ - // hash: tx.hash as Hex, - // }) - + console.log({ postTx }) // Use the waitUntilTx function to wait for the transaction to be processed - const successfulTxHash = await waitUntilTx({ + const successfulTxHash = await waitUntilTx({ projectID: projectId, txID: postTx.transactionId, }) - console.log({successfulTxHash}) + console.log({ successfulTxHash }) return new Response( JSON.stringify({ success: true, hash: successfulTxHash }), @@ -96,4 +62,4 @@ export async function POST(req: NextRequest) { }, ) } -} \ No newline at end of file +} diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index 71ec0ac0..09eed79e 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -1,34 +1,12 @@ import type { NextRequest } from 'next/server' import { addresses } from 'scrypt' import { syndicate } from '@/config/syndicateClient' -import { waitUntilTx, } from '@/lib' +import { waitUntilTx } from '@/lib' export async function POST(req: NextRequest) { const postsArray = await req.json() - console.log("postArray", postsArray) - - /* DEFENDER CODE */ - - // const credentials = { - // relayerApiKey: process.env.NONCE_API_UNO, - // relayerApiSecret: process.env.NONCE_SECRET_UNO, - // } try { - - /* DEFENDER CODE */ - - // const defenderClient = new Defender(credentials) - // const provider = defenderClient.relaySigner.getProvider() - // const signer = defenderClient.relaySigner.getSigner(provider, { - // speed: 'fast', - // }) - - // const postGateway = new ethers.Contract( - // addresses.postGateway.nova, - // postGatewayABI, - // ) - const projectId = process.env.SYNDICATE_PROJECT_ID_POSTGATEWAY if (!projectId) { @@ -48,19 +26,12 @@ export async function POST(req: NextRequest) { }, }) - // Use the waitUntilTx function to wait for the transaction to be processed - const successfulTxHash = await waitUntilTx({ + // Use the waitUntilTx function to wait for the transaction to be processed + const successfulTxHash = await waitUntilTx({ projectID: projectId, txID: postBatchTx.transactionId, }) - /* DEFENDER CODE */ - - // const tx = await postGateway.postBatch(postsArray) - // await novaPubClient.waitForTransactionReceipt({ - // hash: tx.hash as Hex, - // }) - return new Response( JSON.stringify({ success: true, hash: successfulTxHash }), { diff --git a/apps/site/app/api/registerFor/route.ts b/apps/site/app/api/registerFor/route.ts index 792ea3b4..648d0ff5 100644 --- a/apps/site/app/api/registerFor/route.ts +++ b/apps/site/app/api/registerFor/route.ts @@ -1,7 +1,9 @@ +import { optimismPubClient } from '@/config/publicClient' +import { Defender } from '@openzeppelin/defender-sdk' +import { ethers } from 'ethers' import type { NextRequest } from 'next/server' -import { addresses } from 'scrypt' -import { syndicate } from '@/config/syndicateClient' -import { waitUntilTx, } from '@/lib' +import { addresses, idRegistryABI } from 'scrypt' +import { type Hex, decodeAbiParameters } from 'viem' export async function POST(req: NextRequest) { const user = await req.json() @@ -11,80 +13,52 @@ export async function POST(req: NextRequest) { const { to, recovery, deadline, sig } = userWithoutUsername console.log({ userWithoutUsername }) - - /* DEFENDER CODE */ - - // const credentials = { - // relayerApiKey: process.env.IDREGISTRY_API_UNO, - // relayerApiSecret: process.env.IDREGISTRY_SECRET_UNO, - // } + const credentials = { + relayerApiKey: process.env.IDREGISTRY_API_UNO, + relayerApiSecret: process.env.IDREGISTRY_SECRET_UNO, + } try { - /* DEFENDER CODE */ - - // const defenderClient = new Defender(credentials) - // const provider = defenderClient.relaySigner.getProvider() - // const signer = defenderClient.relaySigner.getSigner(provider, { - // speed: 'fast', - // }) - - // const idRegistry = new ethers.Contract( - // addresses.idRegistry.optimism, - // idRegistryABI, - // ) - - /* DEFENDER CODE */ - - - // const registerTxn = await idRegistry.registerFor( - // to, - // recovery, - // deadline, - // sig, - // ) - - const projectId = process.env.SYNDICATE_PROJECT_ID_IDREGISTRY - if (!projectId) { - throw new Error( - 'SYNDICATE_PROJECT_ID is not defined in environment variables.', - ) - } - - const registerTx = await syndicate.transact.sendTransaction({ - projectId: projectId, - contractAddress: addresses.idRegistry.optimism, - chainId: 420, - functionSignature: - 'registerFor(address to, address recovery, uint256 deadline, bytes sig)', - args: { userWithoutUsername }, + const defenderClient = new Defender(credentials) + const provider = defenderClient.relaySigner.getProvider() + const signer = defenderClient.relaySigner.getSigner(provider, { + speed: 'fast', }) - // Use the waitUntilTx function to wait for the transaction to be processed - const successfulTxHash = await waitUntilTx({ - projectID: projectId, - txID: registerTx.transactionId, - }) - + const idRegistry = new ethers.Contract( + addresses.idRegistry.optimism, + idRegistryABI, + signer as unknown as ethers.Signer, + ) - /* DEFENDER CODE */ + const registerTxn = await idRegistry.registerFor( + to, + recovery, + deadline, + sig, + ) - // const txnReceipt = await optimismPubClient.waitForTransactionReceipt({ - // hash: registerTxn.hash as Hex, - // }) + const txnReceipt = await optimismPubClient.waitForTransactionReceipt({ + hash: registerTxn.hash as Hex, + }) - // const [rid, recoveryAddress] = decodeAbiParameters( - // [ - // { name: 'rid', type: 'uint256' }, - // { name: 'recoveryAddress', type: 'address' }, - // ], - // txnReceipt.logs[0].data, - // ) + const [rid, recoveryAddress] = decodeAbiParameters( + [ + { name: 'rid', type: 'uint256' }, + { name: 'recoveryAddress', type: 'address' }, + ], + txnReceipt.logs[0].data, + ) - // console.log('rid: ', rid) + console.log('rid: ', rid) + console.log('transaction receipt: ', registerTxn) - return new Response( - JSON.stringify({ success: true, hash: successfulTxHash }), + JSON.stringify({ + success: true, + hash: registerTxn.hash, + rid: rid.toString(), + }), { status: 200, headers: { 'Content-Type': 'application/json' }, diff --git a/apps/site/lib/api.ts b/apps/site/lib/api.ts index 35e4ed0d..482429c0 100644 --- a/apps/site/lib/api.ts +++ b/apps/site/lib/api.ts @@ -51,7 +51,6 @@ export interface SyndicateApiResponse { value: string } - export interface WaitUntilTxOptions { projectID: string txID: string @@ -59,7 +58,10 @@ export interface WaitUntilTxOptions { every?: number } -export const getTransactionRequest = async ({ projectID, txID }: Pick) => { +export const getTransactionRequest = async ({ + projectID, + txID, +}: Pick) => { const response = await fetch( `https://api.syndicate.io/wallet/project/${projectID}/request/${txID}`, { @@ -86,14 +88,20 @@ export async function waitUntilTx({ await new Promise((resolve) => setTimeout(resolve, every)) if (currAttempts >= maxAttempts) { - throw new Error("Max attempts reached") + throw new Error('Max attempts reached') } - const txAttempts = (await getTransactionRequest({ projectID, txID }))?.transactionAttempts + const txAttempts = (await getTransactionRequest({ projectID, txID })) + ?.transactionAttempts - console.log({txAttempts}) + console.log({ txAttempts }) - if (txAttempts && txAttempts.length > 0 && txAttempts[txAttempts.length - 1].status === 'PENDING' && !txAttempts[txAttempts.length - 1].reverted) { + if ( + txAttempts && + txAttempts.length > 0 && + txAttempts[txAttempts.length - 1].status === 'PENDING' && + !txAttempts[txAttempts.length - 1].reverted + ) { transactionHash = txAttempts[txAttempts.length - 1].hash console.log(transactionHash) break @@ -105,7 +113,6 @@ export async function waitUntilTx({ return transactionHash } - /* API ROUTES */ // This is in to help with serialization of bigints during json stringify From 87a0e263b4e774e8cc568de8b2ddb736a2344ec5 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Fri, 29 Mar 2024 13:09:36 -0500 Subject: [PATCH 09/18] reviewed changes --- apps/delta/ponder.config.ts | 2 +- apps/site/app/api/post/route.ts | 24 +++---------- apps/site/app/api/postBatch/route.ts | 18 +++------- apps/site/config/syndicateClient.ts | 51 ++++++++++++++++++++++++++++ apps/site/lib/api.ts | 32 ++++++++--------- 5 files changed, 76 insertions(+), 51 deletions(-) diff --git a/apps/delta/ponder.config.ts b/apps/delta/ponder.config.ts index b9b585a9..554a93c3 100644 --- a/apps/delta/ponder.config.ts +++ b/apps/delta/ponder.config.ts @@ -1,6 +1,6 @@ import { createConfig } from '@ponder/core' import { addresses, idRegistryABI, postGatewayABI } from 'scrypt' -import { Hex, http } from 'viem' +import { http } from 'viem' export default createConfig({ networks: { diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index c5838e93..a2692b83 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -1,41 +1,27 @@ import type { NextRequest } from 'next/server' -import { syndicate } from '@/config/syndicateClient' -import { addresses } from 'scrypt' +import { syndicate, postObject, projectId } from '@/config/syndicateClient' import { waitUntilTx } from '@/lib' export async function POST(req: NextRequest) { const post = await req.json() try { - const projectId = process.env.SYNDICATE_PROJECT_ID_POSTGATEWAY - if (!projectId) { throw new Error( 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', ) } - const postTx = await syndicate.transact.sendTransaction({ - projectId: projectId, - contractAddress: addresses.postGateway.nova, - chainId: 42170, - functionSignature: - 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig) post)', - args: { - post: post, - }, - }) + const postBatchTxRequest = postObject(post) - console.log({ postTx }) + const postBatchTx = + await syndicate.transact.sendTransaction(postBatchTxRequest) - // Use the waitUntilTx function to wait for the transaction to be processed const successfulTxHash = await waitUntilTx({ projectID: projectId, - txID: postTx.transactionId, + txID: postBatchTx.transactionId, }) - console.log({ successfulTxHash }) - return new Response( JSON.stringify({ success: true, hash: successfulTxHash }), { diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index 09eed79e..3d63c93f 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -1,32 +1,22 @@ import type { NextRequest } from 'next/server' import { addresses } from 'scrypt' -import { syndicate } from '@/config/syndicateClient' +import { syndicate, postBatchObject, projectId } from '@/config/syndicateClient' import { waitUntilTx } from '@/lib' export async function POST(req: NextRequest) { const postsArray = await req.json() try { - const projectId = process.env.SYNDICATE_PROJECT_ID_POSTGATEWAY - if (!projectId) { throw new Error( 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', ) } + const postBatchTxRequest = postBatchObject(postsArray) - const postBatchTx = await syndicate.transact.sendTransaction({ - projectId: projectId, - contractAddress: addresses.postGateway.nova, - chainId: 42170, - functionSignature: - 'postBatch((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig)[] posts)', - args: { - posts: postsArray, - }, - }) + const postBatchTx = + await syndicate.transact.sendTransaction(postBatchTxRequest) - // Use the waitUntilTx function to wait for the transaction to be processed const successfulTxHash = await waitUntilTx({ projectID: projectId, txID: postBatchTx.transactionId, diff --git a/apps/site/config/syndicateClient.ts b/apps/site/config/syndicateClient.ts index 226fed72..e16dccf7 100644 --- a/apps/site/config/syndicateClient.ts +++ b/apps/site/config/syndicateClient.ts @@ -1,4 +1,25 @@ import { SyndicateClient } from '@syndicateio/syndicate-node' +import { addresses } from 'scrypt' + +type PostMessage = { + rid: bigint + timestamp: bigint + msgType: number + msgBody: string +} + +type Post = { + signer: string + message: PostMessage + hashType: number + hash: string + sigType: number + sig: string +} + +type PostBatchFunction = { + posts: Post[] +} export const syndicate = new SyndicateClient({ token: () => { @@ -11,3 +32,33 @@ export const syndicate = new SyndicateClient({ return apiKey }, }) + +export const projectId = process.env.SYNDICATE_PROJECT_ID_POSTGATEWAY + +if (!projectId) { + throw new Error( + 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', + ) +} + +export const postBatchObject = (postsArray: PostBatchFunction) => ({ + projectId: projectId, + contractAddress: addresses.postGateway.nova, + chainId: 42170, + functionSignature: + 'postBatch((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig)[] posts)', + args: { + posts: postsArray, + }, +}) + +export const postObject = (post: Post) => ({ + projectId: projectId, + contractAddress: addresses.postGateway.nova, + chainId: 42170, + functionSignature: + 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig) post)', + args: { + posts: post, + }, +}) diff --git a/apps/site/lib/api.ts b/apps/site/lib/api.ts index 482429c0..3dacaa96 100644 --- a/apps/site/lib/api.ts +++ b/apps/site/lib/api.ts @@ -84,30 +84,28 @@ export async function waitUntilTx({ let currAttempts = 0 let transactionHash = null - while (!transactionHash) { - await new Promise((resolve) => setTimeout(resolve, every)) - - if (currAttempts >= maxAttempts) { - throw new Error('Max attempts reached') - } - + while (!transactionHash && currAttempts < maxAttempts) { const txAttempts = (await getTransactionRequest({ projectID, txID })) ?.transactionAttempts console.log({ txAttempts }) - if ( - txAttempts && - txAttempts.length > 0 && - txAttempts[txAttempts.length - 1].status === 'PENDING' && - !txAttempts[txAttempts.length - 1].reverted - ) { - transactionHash = txAttempts[txAttempts.length - 1].hash - console.log(transactionHash) - break + if (txAttempts && txAttempts.length > 0) { + const lastAttempt = txAttempts[txAttempts.length - 1] + if (lastAttempt.status === 'PENDING' && !lastAttempt.reverted) { + transactionHash = lastAttempt.hash + break + } } - currAttempts += 1 + currAttempts++ + if (!transactionHash && currAttempts < maxAttempts) { + await new Promise((resolve) => setTimeout(resolve, every)) + } + } + + if (!transactionHash) { + throw new Error('Transaction not found within maximum attempts') } return transactionHash From 063a335b01a1bf857bd70b9e70c53f9616055972 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Fri, 29 Mar 2024 13:20:38 -0500 Subject: [PATCH 10/18] post fix --- apps/site/config/syndicateClient.ts | 19 ++++++++++--------- 1 file changed, 10 insertions(+), 9 deletions(-) diff --git a/apps/site/config/syndicateClient.ts b/apps/site/config/syndicateClient.ts index e16dccf7..8b598781 100644 --- a/apps/site/config/syndicateClient.ts +++ b/apps/site/config/syndicateClient.ts @@ -53,12 +53,13 @@ export const postBatchObject = (postsArray: PostBatchFunction) => ({ }) export const postObject = (post: Post) => ({ - projectId: projectId, - contractAddress: addresses.postGateway.nova, - chainId: 42170, - functionSignature: - 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig) post)', - args: { - posts: post, - }, -}) + projectId: projectId, + contractAddress: addresses.postGateway.nova, + chainId: 42170, + functionSignature: + 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig) post)', + args: { + post: post, + }, + }) + \ No newline at end of file From b5e0ef7669e02ea522b20f6daf881e6b3e851be8 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Fri, 29 Mar 2024 13:21:18 -0500 Subject: [PATCH 11/18] post fix --- apps/site/app/api/post/route.ts | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index a2692b83..e8a5f611 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -12,14 +12,14 @@ export async function POST(req: NextRequest) { ) } - const postBatchTxRequest = postObject(post) + const postTxRequest = postObject(post) - const postBatchTx = - await syndicate.transact.sendTransaction(postBatchTxRequest) + const postTx = + await syndicate.transact.sendTransaction(postTxRequest) const successfulTxHash = await waitUntilTx({ projectID: projectId, - txID: postBatchTx.transactionId, + txID: post.transactionId, }) return new Response( From dd8316d0599580d548c25fe3462f00e5aaca35f7 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Fri, 29 Mar 2024 13:23:48 -0500 Subject: [PATCH 12/18] format and lint --- apps/site/app/api/post/route.ts | 3 +-- apps/site/config/syndicateClient.ts | 19 +++++++++---------- 2 files changed, 10 insertions(+), 12 deletions(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index e8a5f611..a44caaa9 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -14,8 +14,7 @@ export async function POST(req: NextRequest) { const postTxRequest = postObject(post) - const postTx = - await syndicate.transact.sendTransaction(postTxRequest) + const postTx = await syndicate.transact.sendTransaction(postTxRequest) const successfulTxHash = await waitUntilTx({ projectID: projectId, diff --git a/apps/site/config/syndicateClient.ts b/apps/site/config/syndicateClient.ts index 8b598781..6cb83e16 100644 --- a/apps/site/config/syndicateClient.ts +++ b/apps/site/config/syndicateClient.ts @@ -53,13 +53,12 @@ export const postBatchObject = (postsArray: PostBatchFunction) => ({ }) export const postObject = (post: Post) => ({ - projectId: projectId, - contractAddress: addresses.postGateway.nova, - chainId: 42170, - functionSignature: - 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig) post)', - args: { - post: post, - }, - }) - \ No newline at end of file + projectId: projectId, + contractAddress: addresses.postGateway.nova, + chainId: 42170, + functionSignature: + 'post((address signer, (uint256 rid, uint256 timestamp, uint8 msgType, bytes msgBody) message, uint16 hashType, bytes32 hash, uint16 sigType, bytes sig) post)', + args: { + post: post, + }, +}) From 4dbf651b50ed1cec0df406569bdb0cfc7a8c6b18 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Fri, 29 Mar 2024 13:26:26 -0500 Subject: [PATCH 13/18] post fix in hash --- apps/site/app/api/post/route.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index a44caaa9..c289f41a 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -18,7 +18,7 @@ export async function POST(req: NextRequest) { const successfulTxHash = await waitUntilTx({ projectID: projectId, - txID: post.transactionId, + txID: postTx.transactionId, }) return new Response( From 5813ab27370110a8f228acd45619ae0b0b9e18b5 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Mon, 1 Apr 2024 11:43:03 -0500 Subject: [PATCH 14/18] passing authToken as prop --- apps/site/app/api/post/route.ts | 15 +++++++++------ apps/site/app/api/postBatch/route.ts | 14 +++++++++----- apps/site/config/syndicateClient.ts | 10 ++++++---- apps/site/lib/api.ts | 12 +++++++++--- 4 files changed, 33 insertions(+), 18 deletions(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index c289f41a..af01d5e6 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -1,17 +1,19 @@ import type { NextRequest } from 'next/server' import { syndicate, postObject, projectId } from '@/config/syndicateClient' -import { waitUntilTx } from '@/lib' +import { waitUntilTx, authToken} from '@/lib' export async function POST(req: NextRequest) { const post = await req.json() try { - if (!projectId) { - throw new Error( - 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', - ) + if (!projectId || typeof projectId !== 'string') { + throw new Error('projectId must be defined and of type string') } - + + if (!authToken || typeof authToken !== 'string') { + throw new Error('authToken must be defined and of type string') + } + const postTxRequest = postObject(post) const postTx = await syndicate.transact.sendTransaction(postTxRequest) @@ -19,6 +21,7 @@ export async function POST(req: NextRequest) { const successfulTxHash = await waitUntilTx({ projectID: projectId, txID: postTx.transactionId, + authToken }) return new Response( diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index 3d63c93f..04dd9740 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -1,17 +1,20 @@ import type { NextRequest } from 'next/server' import { addresses } from 'scrypt' import { syndicate, postBatchObject, projectId } from '@/config/syndicateClient' -import { waitUntilTx } from '@/lib' +import { waitUntilTx, authToken } from '@/lib' export async function POST(req: NextRequest) { const postsArray = await req.json() try { - if (!projectId) { - throw new Error( - 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', - ) + if (!projectId || typeof projectId !== 'string') { + throw new Error('projectId must be defined and of type string'); } + + if (!authToken || typeof authToken !== 'string') { + throw new Error('authToken must be defined and of type string'); + } + const postBatchTxRequest = postBatchObject(postsArray) const postBatchTx = @@ -20,6 +23,7 @@ export async function POST(req: NextRequest) { const successfulTxHash = await waitUntilTx({ projectID: projectId, txID: postBatchTx.transactionId, + authToken }) return new Response( diff --git a/apps/site/config/syndicateClient.ts b/apps/site/config/syndicateClient.ts index 6cb83e16..234bbc67 100644 --- a/apps/site/config/syndicateClient.ts +++ b/apps/site/config/syndicateClient.ts @@ -33,13 +33,15 @@ export const syndicate = new SyndicateClient({ }, }) + + export const projectId = process.env.SYNDICATE_PROJECT_ID_POSTGATEWAY if (!projectId) { - throw new Error( - 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', - ) -} + throw new Error( + 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', + ) + } export const postBatchObject = (postsArray: PostBatchFunction) => ({ projectId: projectId, diff --git a/apps/site/lib/api.ts b/apps/site/lib/api.ts index 3dacaa96..83325270 100644 --- a/apps/site/lib/api.ts +++ b/apps/site/lib/api.ts @@ -54,19 +54,24 @@ export interface SyndicateApiResponse { export interface WaitUntilTxOptions { projectID: string txID: string + authToken: string maxAttempts?: number every?: number } +export const authToken = process.env.SYNDICATE_API_KEY + + export const getTransactionRequest = async ({ projectID, txID, -}: Pick) => { + authToken, +}: Pick & { authToken: string }) => { const response = await fetch( `https://api.syndicate.io/wallet/project/${projectID}/request/${txID}`, { method: 'GET', - headers: { Authorization: `Bearer ${process.env.SYNDICATE_API_KEY}` }, + headers: { Authorization: `Bearer ${authToken}` }, }, ) if (!response.ok) { @@ -78,6 +83,7 @@ export const getTransactionRequest = async ({ export async function waitUntilTx({ projectID, txID, + authToken, maxAttempts = 20, every = 1000, }: WaitUntilTxOptions) { @@ -85,7 +91,7 @@ export async function waitUntilTx({ let transactionHash = null while (!transactionHash && currAttempts < maxAttempts) { - const txAttempts = (await getTransactionRequest({ projectID, txID })) + const txAttempts = (await getTransactionRequest({ projectID, txID, authToken })) ?.transactionAttempts console.log({ txAttempts }) From 6632a9a13cc8a8ce4036f022943366ffc0702881 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Mon, 1 Apr 2024 11:45:33 -0500 Subject: [PATCH 15/18] format & lint --- apps/site/app/api/post/route.ts | 8 ++++---- apps/site/app/api/postBatch/route.ts | 10 +++++----- apps/site/config/syndicateClient.ts | 10 ++++------ apps/site/lib/api.ts | 8 ++++---- 4 files changed, 17 insertions(+), 19 deletions(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index af01d5e6..72d93112 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -1,6 +1,6 @@ import type { NextRequest } from 'next/server' import { syndicate, postObject, projectId } from '@/config/syndicateClient' -import { waitUntilTx, authToken} from '@/lib' +import { waitUntilTx, authToken } from '@/lib' export async function POST(req: NextRequest) { const post = await req.json() @@ -9,11 +9,11 @@ export async function POST(req: NextRequest) { if (!projectId || typeof projectId !== 'string') { throw new Error('projectId must be defined and of type string') } - + if (!authToken || typeof authToken !== 'string') { throw new Error('authToken must be defined and of type string') } - + const postTxRequest = postObject(post) const postTx = await syndicate.transact.sendTransaction(postTxRequest) @@ -21,7 +21,7 @@ export async function POST(req: NextRequest) { const successfulTxHash = await waitUntilTx({ projectID: projectId, txID: postTx.transactionId, - authToken + authToken, }) return new Response( diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index 04dd9740..14f2120a 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -8,13 +8,13 @@ export async function POST(req: NextRequest) { try { if (!projectId || typeof projectId !== 'string') { - throw new Error('projectId must be defined and of type string'); + throw new Error('projectId must be defined and of type string') } - + if (!authToken || typeof authToken !== 'string') { - throw new Error('authToken must be defined and of type string'); + throw new Error('authToken must be defined and of type string') } - + const postBatchTxRequest = postBatchObject(postsArray) const postBatchTx = @@ -23,7 +23,7 @@ export async function POST(req: NextRequest) { const successfulTxHash = await waitUntilTx({ projectID: projectId, txID: postBatchTx.transactionId, - authToken + authToken, }) return new Response( diff --git a/apps/site/config/syndicateClient.ts b/apps/site/config/syndicateClient.ts index 234bbc67..6cb83e16 100644 --- a/apps/site/config/syndicateClient.ts +++ b/apps/site/config/syndicateClient.ts @@ -33,15 +33,13 @@ export const syndicate = new SyndicateClient({ }, }) - - export const projectId = process.env.SYNDICATE_PROJECT_ID_POSTGATEWAY if (!projectId) { - throw new Error( - 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', - ) - } + throw new Error( + 'SYNDICATE_PROJECT_ID_POSTGATEWAY is not defined in environment variables.', + ) +} export const postBatchObject = (postsArray: PostBatchFunction) => ({ projectId: projectId, diff --git a/apps/site/lib/api.ts b/apps/site/lib/api.ts index 83325270..e155eb8c 100644 --- a/apps/site/lib/api.ts +++ b/apps/site/lib/api.ts @@ -61,12 +61,11 @@ export interface WaitUntilTxOptions { export const authToken = process.env.SYNDICATE_API_KEY - export const getTransactionRequest = async ({ projectID, txID, authToken, -}: Pick & { authToken: string }) => { +}: Pick & { authToken: string }) => { const response = await fetch( `https://api.syndicate.io/wallet/project/${projectID}/request/${txID}`, { @@ -91,8 +90,9 @@ export async function waitUntilTx({ let transactionHash = null while (!transactionHash && currAttempts < maxAttempts) { - const txAttempts = (await getTransactionRequest({ projectID, txID, authToken })) - ?.transactionAttempts + const txAttempts = ( + await getTransactionRequest({ projectID, txID, authToken }) + )?.transactionAttempts console.log({ txAttempts }) From f80ea1159a8dae32927dfa31bc358a91ab03f6e6 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Mon, 1 Apr 2024 21:49:19 -0500 Subject: [PATCH 16/18] revisions --- apps/site/app/api/post/route.ts | 39 ++++++++++++++++--------- apps/site/app/api/postBatch/route.ts | 43 +++++++++++++++++----------- apps/site/config/syndicateClient.ts | 36 ++++++++++++++--------- 3 files changed, 73 insertions(+), 45 deletions(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index 72d93112..8efe5d9c 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -1,27 +1,38 @@ import type { NextRequest } from 'next/server' -import { syndicate, postObject, projectId } from '@/config/syndicateClient' +import { + syndicateClient, + generatePostTxnInput, + projectId, +} from '@/config/syndicateClient' import { waitUntilTx, authToken } from '@/lib' export async function POST(req: NextRequest) { const post = await req.json() - try { - if (!projectId || typeof projectId !== 'string') { - throw new Error('projectId must be defined and of type string') - } - - if (!authToken || typeof authToken !== 'string') { - throw new Error('authToken must be defined and of type string') - } - - const postTxRequest = postObject(post) + if (!syndicateClient) { + return new Response( + JSON.stringify({ + success: false, + hash: null, + error: 'Syndicate client not initialized', + }), + { + status: 500, + headers: { 'Content-Type': 'application/json' }, + }, + ) + } - const postTx = await syndicate.transact.sendTransaction(postTxRequest) + try { + const postTx = + await syndicateClient.officialActions.transact.sendTransaction( + generatePostTxnInput(post), + ) const successfulTxHash = await waitUntilTx({ - projectID: projectId, + projectID: projectId as string, txID: postTx.transactionId, - authToken, + authToken: authToken as string, }) return new Response( diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index 14f2120a..0c3f19c1 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -1,29 +1,38 @@ import type { NextRequest } from 'next/server' -import { addresses } from 'scrypt' -import { syndicate, postBatchObject, projectId } from '@/config/syndicateClient' +import { + syndicateClient, + generatePostBatchTxnInput, + projectId, +} from '@/config/syndicateClient' import { waitUntilTx, authToken } from '@/lib' export async function POST(req: NextRequest) { const postsArray = await req.json() - try { - if (!projectId || typeof projectId !== 'string') { - throw new Error('projectId must be defined and of type string') - } - - if (!authToken || typeof authToken !== 'string') { - throw new Error('authToken must be defined and of type string') - } - - const postBatchTxRequest = postBatchObject(postsArray) + if (!syndicateClient) { + return new Response( + JSON.stringify({ + success: false, + hash: null, + error: 'Syndicate client not initialized', + }), + { + status: 500, + headers: { 'Content-Type': 'application/json' }, + }, + ) + } - const postBatchTx = - await syndicate.transact.sendTransaction(postBatchTxRequest) + try { + const postTx = + await syndicateClient.officialActions.transact.sendTransaction( + generatePostBatchTxnInput({ posts: postsArray }), + ) const successfulTxHash = await waitUntilTx({ - projectID: projectId, - txID: postBatchTx.transactionId, - authToken, + projectID: projectId as string, + txID: postTx.transactionId, + authToken: authToken as string, }) return new Response( diff --git a/apps/site/config/syndicateClient.ts b/apps/site/config/syndicateClient.ts index 6cb83e16..e2860b69 100644 --- a/apps/site/config/syndicateClient.ts +++ b/apps/site/config/syndicateClient.ts @@ -21,18 +21,6 @@ type PostBatchFunction = { posts: Post[] } -export const syndicate = new SyndicateClient({ - token: () => { - const apiKey = process.env.SYNDICATE_API_KEY - if (typeof apiKey === 'undefined') { - throw new Error( - 'SYNDICATE_API_KEY is not defined in environment variables.', - ) - } - return apiKey - }, -}) - export const projectId = process.env.SYNDICATE_PROJECT_ID_POSTGATEWAY if (!projectId) { @@ -41,7 +29,7 @@ if (!projectId) { ) } -export const postBatchObject = (postsArray: PostBatchFunction) => ({ +export const generatePostBatchTxnInput = (postsArray: PostBatchFunction) => ({ projectId: projectId, contractAddress: addresses.postGateway.nova, chainId: 42170, @@ -52,7 +40,7 @@ export const postBatchObject = (postsArray: PostBatchFunction) => ({ }, }) -export const postObject = (post: Post) => ({ +export const generatePostTxnInput = (post: Post) => ({ projectId: projectId, contractAddress: addresses.postGateway.nova, chainId: 42170, @@ -62,3 +50,23 @@ export const postObject = (post: Post) => ({ post: post, }, }) + +const apiKey = process.env.SYNDICATE_API_KEY + +export const syndicateClient = + !projectId || !apiKey + ? null + : { + officialActions: new SyndicateClient({ + token: () => apiKey, + }), + projectId: projectId, + generatePostTxnInput, + generatePostBatchTxnInput, + } + +if (!projectId || !apiKey) { + throw new Error( + 'Missing SYNDICATE_PROJECT_ID_POSTGATEWAY or SYNDICATE_API_KEY in environment variables.', + ) +} From 469a1627fc0ec68bf645ce1d5cad792e79a0615d Mon Sep 17 00:00:00 2001 From: jawndiego Date: Tue, 2 Apr 2024 05:34:17 -0500 Subject: [PATCH 17/18] fixes, but stuck w. api. no test --- apps/site/app/api/post/route.ts | 3 +++ apps/site/app/api/postBatch/route.ts | 2 +- 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index 8efe5d9c..cf14b591 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -29,6 +29,9 @@ export async function POST(req: NextRequest) { generatePostTxnInput(post), ) + console.log({ syndicateClient }) + console.log({ postTx }) + const successfulTxHash = await waitUntilTx({ projectID: projectId as string, txID: postTx.transactionId, diff --git a/apps/site/app/api/postBatch/route.ts b/apps/site/app/api/postBatch/route.ts index 0c3f19c1..47c5e179 100644 --- a/apps/site/app/api/postBatch/route.ts +++ b/apps/site/app/api/postBatch/route.ts @@ -26,7 +26,7 @@ export async function POST(req: NextRequest) { try { const postTx = await syndicateClient.officialActions.transact.sendTransaction( - generatePostBatchTxnInput({ posts: postsArray }), + generatePostBatchTxnInput(postsArray), ) const successfulTxHash = await waitUntilTx({ From 34391e7bbde02440e5ffd167b0a186e54b098b42 Mon Sep 17 00:00:00 2001 From: jawndiego Date: Tue, 2 Apr 2024 21:56:22 -0500 Subject: [PATCH 18/18] lint format fix. pending patch --- apps/site/app/api/post/route.ts | 3 --- 1 file changed, 3 deletions(-) diff --git a/apps/site/app/api/post/route.ts b/apps/site/app/api/post/route.ts index cf14b591..8efe5d9c 100644 --- a/apps/site/app/api/post/route.ts +++ b/apps/site/app/api/post/route.ts @@ -29,9 +29,6 @@ export async function POST(req: NextRequest) { generatePostTxnInput(post), ) - console.log({ syndicateClient }) - console.log({ postTx }) - const successfulTxHash = await waitUntilTx({ projectID: projectId as string, txID: postTx.transactionId,