feat(integration): contract validation, testnet faucet, CID verification, webhook compression#1210
Open
temma02 wants to merge 1 commit into
Conversation
…ion, webhook compression Implements four integration improvements across the backend: **Emmyt24#1169 — Validate deployed contract addresses match the active environment** - Add `backend/src/lib/contractAddressValidator.ts` with `validateContractOnNetwork()`, which calls the Soroban JSON-RPC `getLedgerEntries` endpoint to confirm the configured contract ID exists on the active network at startup. - The LedgerKey XDR is constructed locally (no external SDK dependency) by decoding the Soroban StrKey contract ID and building the binary key. - Retries on transient network errors with exponential backoff (3 attempts, 1 s base, ×2 factor); throws `ContractAddressError` immediately on format errors or missing contracts with a message that names the contract ID and STELLAR_NETWORK for operator diagnosis. - Tests cover: existing contract, missing contract (empty entries), empty/ malformed IDs (no RPC call made), transient retry, exhaustion, 4xx non-retryable, and correct JSON-RPC method/key format. **Emmyt24#1168 — Integrate the Stellar testnet faucet for automated test setup** - Add `backend/src/lib/testnet-faucet.ts` with: - `generateTestKeypair()` — generates a random Ed25519 keypair using Node.js `crypto` and encodes it as Stellar StrKey (G.../S... 56 chars) with CRC-16/XModem checksum; no external SDK required. - `fundTestAccount(publicKey, network, friendbotUrl)` — calls the Stellar Friendbot faucet; treats HTTP 400 (already funded) as success; retries on transient errors; throws `FaucetError` on non-testnet to prevent accidental mainnet calls. - `generateAndFundKeypair()` — composes the two helpers for test setup. - Tests cover: mainnet/undefined guard, successful funding, transaction hash propagation, HTTP 400 treated as success, retry on ECONNRESET/ETIMEDOUT, exhaustion after max attempts, public-key inclusion in error, no retry on non-retryable 5xx, keypair format (G.../S..., 56 chars, uniqueness), and the combined generateAndFundKeypair flow. **Emmyt24#1170 — Verify IPFS content addressing matches the returned CID** - Add `backend/src/lib/ipfs/cidVerification.ts` with: - `verifyCIDContent(content, cid, gatewayBaseUrl)` — fetches the content stored under the CID from an IPFS gateway and compares it byte-for-byte against the original upload using SHA-256; throws `CIDMismatchError` (includes both hashes) on any mismatch or gateway failure. - `verifyMetadataCID(metadata, cid)` — convenience wrapper that serialises the object with `JSON.stringify` before comparing. - Modify `backend/src/lib/ipfs/pinata.ts`: - Call `verifyCIDContent` after `pinFileToIPFS` and `verifyMetadataCID` after `pinJSONToIPFS` when `IPFS_VERIFY_CID=true`. - Gateway URL is configurable via `IPFS_VERIFY_GATEWAY_URL` (default: `https://gateway.pinata.cloud/ipfs`). - Tests cover: matching content, URL construction, CID in error, SHA-256 hashes in error, HTTP non-2xx, network error, error message wrapping, and JSON serialisation fidelity. **Emmyt24#1167 — Compress large webhook payloads to reduce delivery overhead** - Modify `backend/src/services/webhookDeliveryService.ts`: - Gzip-compress payloads whose JSON size meets or exceeds `WEBHOOK_COMPRESSION_THRESHOLD_BYTES` (default: 1024 bytes, instance- level so tests can override via env before construction). - Set `Content-Encoding: gzip` on compressed deliveries. - On HTTP 415 (Unsupported Media Type) the service clears the encoding and retries immediately with the uncompressed body; the existing 4xx non-retry rule continues to apply to all other 4xx codes. - Tests cover: no compression below threshold, `Content-Encoding: gzip` above threshold, successful end-to-end compressed delivery, and the 415 fallback round-trip showing gzip on attempt 1 and no encoding on attempt 2. Closes Emmyt24#1167 Closes Emmyt24#1168 Closes Emmyt24#1169 Closes Emmyt24#1170
|
@temma02 Great news! 🎉 Based on an automated assessment of this PR, the linked Wave issue(s) no longer count against your application limits. You can now already apply to more issues while waiting for a review of this PR. Keep up the great work! 🚀 |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Implements four integration improvements across the backend service:
getLedgerEntriesendpoint; fail fast with a clear, operator-readable error on mismatch or missing contract.IPFS_VERIFY_CID=true); throws aCIDMismatchErrorwith both SHA-256 hashes on mismatch.WEBHOOK_COMPRESSION_THRESHOLD_BYTES, default 1024); setContent-Encoding: gzip; fall back to uncompressed on HTTP 415 from the consumer.Changes
backend/src/lib/contractAddressValidator.tsbackend/src/lib/testnet-faucet.tsbackend/src/lib/ipfs/cidVerification.tsbackend/src/lib/ipfs/pinata.tsIPFS_VERIFY_CID=truebackend/src/services/webhookDeliveryService.tsbackend/src/__tests__/contractAddressValidator.test.tsbackend/src/__tests__/testnetFaucet.test.tsbackend/src/__tests__/cidVerification.test.tsbackend/src/__tests__/webhookCompression.test.tsHow it was verified
vitest run) using mocked external services (nock for HTTP, vi.fn() for fetch/Pinata).calculateBackoffDelay/isRetryableError/sleeputilities fromstellar-service-integration/rate-limiter.ts.Configuration
IPFS_VERIFY_CIDfalsetrueto enable post-upload CID content verificationIPFS_VERIFY_GATEWAY_URLhttps://gateway.pinata.cloud/ipfsWEBHOOK_COMPRESSION_THRESHOLD_BYTES1024Closes #1167
Closes #1168
Closes #1169
Closes #1170