Skip to content

Main - #64

Merged
AnilChinchawale merged 4 commits into
XinFinOrg:mainfrom
rajshah1609:main
Jul 6, 2026
Merged

Main#64
AnilChinchawale merged 4 commits into
XinFinOrg:mainfrom
rajshah1609:main

Conversation

@rajshah1609

@rajshah1609 rajshah1609 commented Jul 3, 2026

Copy link
Copy Markdown
Member

Summary by CodeRabbit

  • New Features

    • Added enterprise credential setup and secure KYC submission flows.
    • Added a balance lookup endpoint for voter addresses.
  • Bug Fixes

    • Improved balance retrieval by falling back to a server-side lookup when local balance checks fail.
    • Tightened file upload checks to accept PDF files only.
  • Refactor

    • Updated several account, wallet, and signing flows for clearer behavior without changing the user experience.

@coderabbitai

coderabbitai Bot commented Jul 3, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

Warning

Review limit reached

@rajshah1609, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 42 minutes

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 4b97df39-50ca-4abe-9504-e49319c86b0d

📥 Commits

Reviewing files that changed from the base of the PR and between 6014f38 and 92ef781.

📒 Files selected for processing (8)
  • apis/enterprise.js
  • apis/ipfs.js
  • apis/voters.js
  • app/app.js
  • crawl.js
  • models/blockchain/web3rpc.js
  • models/mongodb/enterpriseKey.js
  • models/mongodb/enterpriseNonce.js
📝 Walkthrough

Walkthrough

Adds a new enterprise API (key issuance and authenticated PDF KYC upload to IPFS) with a supporting Mongoose model, adds a voter balance-lookup endpoint used by client wallet balance fallback, adds PDF-only validation to an existing IPFS upload route, and includes unrelated formatting refactors, an RPC URL fallback fix, and a crawler DB lookup removal.

Changes

Enterprise Credentialing and KYC Submission

Layer / File(s) Summary
EnterpriseKey model
models/mongodb/enterpriseKey.js
New Mongoose schema/model storing apiKey (unique), apiSecret, enterpriseName with timestamps.
API key issuance endpoint
apis/enterprise.js
POST /keys validates a master bearer token and enterpriseName, generates and stores apiKey/apiSecret, returns 201 with credentials.
Authenticated KYC upload to IPFS
apis/enterprise.js, apis/index.js
POST /addKYC verifies HMAC signature/timestamp window, validates uploaded PDF (type/size), uploads to IPFS, returns hash; router exported and mounted at /api/enterprise.
PDF-only validation on existing route
apis/ipfs.js
Adds an early check rejecting non-PDF uploads in the existing /addKYC route.

Estimated code review effort: 3 (Moderate) | ~25 minutes

Voter Balance Endpoint and Client Integration

Layer / File(s) Summary
getBalance endpoint
apis/voters.js
New GET /getBalance/:address tries two RPC address formats, returns resolved balance or 500 on total failure.
Client balance fallback wiring
app/app.js
getBalanceSafe() calls the new endpoint first, falling back to existing RPC probing on failure.

Estimated code review effort: 2 (Simple) | ~10 minutes

Unrelated Fixes and Refactors

Layer / File(s) Summary
Wallet provider handling refactor
app/app.js, app/components/candidates/Apply.vue
Ledger signature formatting, modal close scheduling, getAccount/detectNetwork switches, and signMessage Ledger branch reformatted with equivalent behavior.
Internal RPC URL fallback
models/blockchain/web3rpc.js
Web3RpcInternal falls back to blockchain.rpc when blockchain.internalRpc is unset.
Crawler candidate lookup removal
crawl.js
Removes a db.Candidate.findOne prefetch in updateCandidateInfo's non-zero address branch.

Estimated code review effort: 2 (Simple) | ~12 minutes

Sequence Diagram(s)

sequenceDiagram
  participant Client
  participant EnterpriseRouter
  participant EnterpriseKeyDB
  participant IPFS

  Client->>EnterpriseRouter: POST /keys (Bearer masterToken, enterpriseName)
  EnterpriseRouter->>EnterpriseRouter: validate token & enterpriseName
  EnterpriseRouter->>EnterpriseKeyDB: store apiKey/apiSecret
  EnterpriseRouter-->>Client: 201 { apiKey, apiSecret }

  Client->>EnterpriseRouter: POST /addKYC (x-api-key, timestamp, signature, PDF file)
  EnterpriseRouter->>EnterpriseKeyDB: fetch secret by apiKey
  EnterpriseKeyDB-->>EnterpriseRouter: apiSecret
  EnterpriseRouter->>EnterpriseRouter: verify signature & timestamp
  EnterpriseRouter->>EnterpriseRouter: validate PDF type/size
  EnterpriseRouter->>IPFS: upload file
  IPFS-->>EnterpriseRouter: content hash
  EnterpriseRouter-->>Client: 200 { hash }
Loading

Possibly related PRs

  • XinFinOrg/MasterNode-App#41: Both PRs modify the /addKYC handler in apis/ipfs.js adding/changing pre-upload file validations.
  • XinFinOrg/MasterNode-App#44: Both PRs touch the /addKYC route, with this PR adding PDF-only validation and the related PR changing its auth flow.
  • XinFinOrg/MasterNode-App#60: Both PRs modify the KYC/IPFS upload path, with the related PR changing the /addKYC IPFS upload implementation via a multipart axios helper.

Suggested reviewers: AnilChinchawale, RushabhParmar12, Satishpethani92

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 inconclusive)

Check name Status Explanation Resolution
Title check ❓ Inconclusive The title is too vague and does not describe the actual changes in the pull request. Use a concise, specific title that summarizes the main change, such as enterprise KYC/API key and balance endpoint updates.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 11

🧹 Nitpick comments (2)
crawl.js (1)

196-199: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Remove dead code instead of commenting it out.

The candateInDB lookup was already unused in this function (newStatus/owner are derived from the prevStatus/prevOwner parameters, not this variable), so commenting it out has no functional effect. Delete it outright rather than leaving commented-out code.

♻️ Proposed cleanup
         if (candidate !== 'xdc0000000000000000000000000000000000000000') {
-            // check current status
-            // const candateInDB = await db.Candidate.findOne({
-            //     smartContractAddress: config.get('blockchain.validatorAddress'),
-            //     candidate: candidate
-            // }) || {}
-
             let newStatus = prevStatus || 'STANDBY'
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@crawl.js` around lines 196 - 199, Remove the dead commented-out Candidate
lookup in crawl.js rather than leaving it in place; the unused candateInDB query
is no longer needed in this flow because newStatus and owner come from
prevStatus and prevOwner. Delete the commented block from the function that
handles the candidate status update so the code stays clean and the remaining
logic is easier to follow.
apis/voters.js (1)

28-58: 🚀 Performance & Scalability | 🔵 Trivial | ⚡ Quick win

Redundant RPC round-trip when the first lookup already succeeds.

Both web3.eth.getBalance(rpcAddr) and web3.eth.getBalance(xdcAddr) are called unconditionally, even when the first call already returns a valid non-zero balance. This doubles RPC load per request for the common case.

♻️ Short-circuit the second call when the first already returned a usable value
         try {
             balance0x = await web3.eth.getBalance(rpcAddr)
             success = true
         } catch (e) {}

-        try {
-            balanceXdc = await web3.eth.getBalance(xdcAddr)
-            success = true
-        } catch (e) {}
+        if (!balance0x || balance0x === '0' || balance0x === '0x0') {
+            try {
+                balanceXdc = await web3.eth.getBalance(xdcAddr)
+                success = true
+            } catch (e) {}
+        }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@apis/voters.js` around lines 28 - 58, The getBalance route in voters.js
always performs both web3.eth.getBalance calls even after the first one
succeeds, causing an unnecessary extra RPC round-trip. Update the balance lookup
logic in the router.get('/getBalance/:address') handler to short-circuit after
the first successful, usable result by checking balance0x before querying
xdcAddr, while keeping the existing fallback and error handling behavior in
place.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@apis/enterprise.js`:
- Around line 102-106: The HMAC validation in enterprise.js is currently bound
only to method, path, and timestamp, which allows a valid signature to be
replayed with a different uploaded PDF within the timestamp window. Update the
signature flow around stringToSign to incorporate a digest of the request body
(or uploaded file content) and, if helpful, file metadata such as filename and
size; also add a nonce or idempotency key to prevent replay. Make sure both the
signature generation and the verification logic in the same request validation
path use the same expanded signed payload.
- Around line 142-144: The KYC upload flow in the enterprise handler is logging
the IPFS content hash, which should not be emitted to application logs. Update
the logic in the enterprise KYC upload path so the authenticated response still
returns the hash from the upload result, but remove or redact it from the
console output in the KYC handler. Use the existing upload/responder code around
the hash assignment and response send to keep the behavior unchanged except for
logging.
- Around line 124-127: The file validation in the uploaded-file check is too
permissive because the `&&` in the `enterprise.js` PDF guard allows a file
through if either the MIME type or filename looks like PDF; update the condition
in the upload handler to require both checks to pass by using `||` for
rejection, and if possible strengthen the `uploadedFile` validation further by
verifying the PDF magic bytes in addition to the existing MIME/extension checks.
- Around line 20-24: The IPFS upload in axios.post within the addKYC flow has no
timeout, so a stalled endpoint can hang the request indefinitely. Add an
explicit timeout to the axios.post call in the IPFS upload path and keep the
existing headers/maxBodyLength/maxContentLength settings intact. Use the
axios.post invocation in the enterprise.js flow as the place to apply the
timeout so the /addKYC request fails cleanly instead of hanging.
- Around line 113-114: The signature check in the enterprise API path uses a
plain string comparison, so update the logic around the
`apiSignature`/`expectedSignature` check to use constant-time HMAC verification
instead. Decode both hex digests, reject malformed or length-mismatched values
before comparing, and use `crypto.timingSafeEqual` in the `unauthorized(res,
'invalid_signature')` flow to preserve the existing failure behavior.

In `@apis/ipfs.js`:
- Around line 157-160: The PDF validation in the IPFS upload flow is too
permissive because the check in the upload handler allows a file through if
either the MIME type or filename matches. Update the condition in the imageFile
validation so it rejects unless both PDF checks pass, and consider adding a PDF
magic-bytes check in the same upload path before the IPFS upload to further
verify the file content.

In `@apis/voters.js`:
- Around line 38-46: The RPC balance lookups in Web3RpcInternal() currently
swallow failures in the two getBalance try/catch blocks, and the HttpProvider is
created without any timeout. Update the catch blocks to log the error details
for both rpcAddr and xdcAddr balance fetches, and configure the Web3
HttpProvider with a timeout so hung or unreachable RPC nodes fail fast instead
of leaving the endpoint silent or blocked.

In `@app/app.js`:
- Line 1483: The signature assignment in the app.js logic has an
operator-precedence bug: the fallback in `result = '0x' + sig.payload.signature
|| ''` never applies. Update the code around the signature formatting path to
explicitly guard `sig.payload.signature` before concatenation, using the
relevant result-building logic where `sig` and `sig.payload.signature` are
handled, so missing values don’t turn into a truthy `"0xundefined"` string.
- Around line 1461-1482: The ledger and trezor branches in the message-signing
switch declare const/let variables directly inside case clauses, which triggers
noSwitchDeclarations and can cause scope/TDZ issues. Wrap the bodies of the
'ledger' and 'trezor' cases in their own blocks, following the same pattern used
by getAccount and detectNetwork, and keep the existing signPersonalMessage,
toHexBuffer, and TrezorConnect.ethereumSignMessage logic inside those blocks.
- Around line 843-852: The getBalanceSafe helper currently makes an axios GET to
/api/voters/getBalance/... without any timeout, which can block the fallback
path if the server or RPC stalls. Update Vue.prototype.getBalanceSafe to pass a
timeout on the axios request so the catch path can run promptly, and keep the
existing fallback logging/context behavior intact.

In `@models/mongodb/enterpriseKey.js`:
- Around line 13-15: The enterprise key model’s apiSecret field is currently
stored and returned in plaintext, so update the EnterpriseKey schema/model to
encrypt and decrypt this value transparently while keeping it excluded from
default projections. Add the necessary schema hooks or getters/setters around
apiSecret in enterpriseKey.js, and make sure any code that reads it for HMAC
verification explicitly opts in to selecting the field when needed.

---

Nitpick comments:
In `@apis/voters.js`:
- Around line 28-58: The getBalance route in voters.js always performs both
web3.eth.getBalance calls even after the first one succeeds, causing an
unnecessary extra RPC round-trip. Update the balance lookup logic in the
router.get('/getBalance/:address') handler to short-circuit after the first
successful, usable result by checking balance0x before querying xdcAddr, while
keeping the existing fallback and error handling behavior in place.

In `@crawl.js`:
- Around line 196-199: Remove the dead commented-out Candidate lookup in
crawl.js rather than leaving it in place; the unused candateInDB query is no
longer needed in this flow because newStatus and owner come from prevStatus and
prevOwner. Delete the commented block from the function that handles the
candidate status update so the code stays clean and the remaining logic is
easier to follow.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: c94fb99c-be00-438b-8dcf-05346ec71494

📥 Commits

Reviewing files that changed from the base of the PR and between 85fd1e3 and 6014f38.

📒 Files selected for processing (9)
  • apis/enterprise.js
  • apis/index.js
  • apis/ipfs.js
  • apis/voters.js
  • app/app.js
  • app/components/candidates/Apply.vue
  • crawl.js
  • models/blockchain/web3rpc.js
  • models/mongodb/enterpriseKey.js

Comment thread apis/enterprise.js
Comment thread apis/enterprise.js Outdated
Comment thread apis/enterprise.js Outdated
Comment thread apis/enterprise.js Outdated
Comment thread apis/enterprise.js
Comment thread apis/voters.js Outdated
Comment on lines +38 to +46
try {
balance0x = await web3.eth.getBalance(rpcAddr)
success = true
} catch (e) {}

try {
balanceXdc = await web3.eth.getBalance(xdcAddr)
success = true
} catch (e) {}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🩺 Stability & Availability | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
set -euo pipefail

printf '\n== apis/voters.js ==\n'
wc -l apis/voters.js
sed -n '1,120p' apis/voters.js

printf '\n== models/blockchain/web3rpc.js ==\n'
wc -l models/blockchain/web3rpc.js
sed -n '1,220p' models/blockchain/web3rpc.js

printf '\n== search for Web3RpcInternal and timeout references ==\n'
rg -n "Web3RpcInternal|timeout|request timeout|rpc timeout|AbortSignal|AbortController" -S .

Repository: XinFinOrg/MasterNode-App

Length of output: 6803


🌐 Web query:

xdc3 HttpProvider timeout options default request timeout Web3.providers.HttpProvider

💡 Result:

In XDC3 (and its underlying web3.js-based architecture), you can configure the request timeout for an HttpProvider by passing a timeout option (in milliseconds) within the provider's options object during instantiation [1]. To set a custom timeout, include it in the options object passed to the XDC3ProvidersHttp constructor [1]: var Web3HttpProvider = require('xdc3-providers-http'); var options = { timeout: 20000, // Timeout in milliseconds keepAlive: true, //... other options }; var provider = new Web3HttpProvider('http://localhost:8545', options); Important distinctions to note: 1. Provider Timeout: The timeout option in HttpProviderOptions refers to the duration (in milliseconds) the HTTP request itself will wait before timing out [1]. 2. Transaction Polling Timeout: There is a separate setting called transactionPollingTimeout available on the web3.eth module [2][3]. This defines the number of seconds the library waits for a transaction receipt to be confirmed on the network when using HTTP connections [2][3]. Its default value is 750 seconds [2][3]. It can be adjusted globally or on contract instances: web3.eth.transactionPollingTimeout = 1000; // Sets the timeout to 1000 seconds [2] Ensure you do not confuse the provider's connection timeout with the transaction polling timeout, as they serve different purposes within the library [2][1].

Citations:


Log RPC failures and set a timeout. Both catch blocks swallow errors, and Web3RpcInternal() instantiates HttpProvider without a timeout, so RPC outages or a hung node can leave this endpoint silent or stuck indefinitely.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@apis/voters.js` around lines 38 - 46, The RPC balance lookups in
Web3RpcInternal() currently swallow failures in the two getBalance try/catch
blocks, and the HttpProvider is created without any timeout. Update the catch
blocks to log the error details for both rpcAddr and xdcAddr balance fetches,
and configure the Web3 HttpProvider with a timeout so hung or unreachable RPC
nodes fail fast instead of leaving the endpoint silent or blocked.

Comment thread app/app.js
Comment thread app/app.js Outdated
Comment thread app/app.js Outdated
Comment thread models/mongodb/enterpriseKey.js Outdated
@AnilChinchawale
AnilChinchawale merged commit fc925b1 into XinFinOrg:main Jul 6, 2026
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants