Handle PayerReportAlreadySubmitted #1246
Merged
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.
Add handling for
PayerReportAlreadySubmittedby mapping revert code0x93105c68toErrPayerReportAlreadySubmittedand updatingpayerreport.workers.SubmitterWorker.SubmitReportsto mark reports submittedThis change introduces a new protocol error
ErrPayerReportAlreadySubmittedwith selector0x93105c68, adds detection methods to the protocol error interfaces and blockchain error type, and updates the payer report submitter to treat this condition as a successful submission. It also extends tests to cover the new and existing revert cases and adjusts expectations accordingly.ErrPayerReportAlreadySubmittedand map selector0x93105c68in the protocol errors dictionary in errors.goProtocolErrorwithIsErrPayerReportAlreadySubmittedand implementblockchain.BlockchainError.IsErrPayerReportAlreadySubmittedin errors.gopayerreport.workers.SubmitterWorker.SubmitReportsto log and mark reports submitted whenIsErrPayerReportAlreadySubmittedis detected in submitter.goPayerReportAlreadySubmitted,InvalidStartSequenceID, andInvalidSequenceIDs, and adjust expectations in submitter_test.go📍Where to Start
Start with the handling in
payerreport.workers.SubmitterWorker.SubmitReportsin submitter.go, then review the new error mapping and detection in errors.go.Changes since #1246 opened
📊 Macroscope summarized 21a5ded. 2 files reviewed, 8 issues evaluated, 8 issues filtered, 0 comments posted
🗂️ Filtered Issues
pkg/blockchain/errors.go — 0 comments posted, 4 evaluated, 4 filtered
protocolErrorsDictionarystores all keys in lowercase (e.g.,"0x93105c68"), while the consumertryExtractProtocolErroruses a case-insensitive regex to extract the code and then performs a direct map lookup without normalizing the matched string. If the input error contains an uppercase hex sequence like0x93105C68, the regex will match it, but the direct lookup with uppercase letters will fail, causingErrCodeNotInDicto be returned even though the code is logically present. The fix is to normalize the matched code to a consistent case (e.g., strings.ToLower) before lookup or to store both cases in the map. [ Low confidence ]protocolErrorsDictionarystores all keys in lowercase (e.g.,"0x93105c68"), while the consumertryExtractProtocolErroruses a case-insensitive regex to extract the code and then performs a direct map lookup without normalizing the matched string. If the input error contains an uppercase hex sequence like0x93105C68, the regex will match it, but the direct lookup with uppercase letters will fail, causingErrCodeNotInDicto be returned even though the code is logically present. The fix is to normalize the matched code to a consistent case (e.g., strings.ToLower) before lookup or to store both cases in the map. [ Low confidence ]protocolErrorsDictionarystores all keys in lowercase (e.g.,"0x93105c68"), while the consumertryExtractProtocolErroruses a case-insensitive regex to extract the code and then performs a direct map lookup without normalizing the matched string. If the input error contains an uppercase hex sequence like0x93105C68, the regex will match it, but the direct lookup with uppercase letters will fail, causingErrCodeNotInDicto be returned even though the code is logically present. The fix is to normalize the matched code to a consistent case (e.g., strings.ToLower) before lookup or to store both cases in the map. [ Low confidence ]protocolErrorsDictionarystores all keys in lowercase (e.g.,"0x93105c68"), while the consumertryExtractProtocolErroruses a case-insensitive regex to extract the code and then performs a direct map lookup without normalizing the matched string. If the input error contains an uppercase hex sequence like0x93105C68, the regex will match it, but the direct lookup with uppercase letters will fail, causingErrCodeNotInDicto be returned even though the code is logically present. The fix is to normalize the matched code to a consistent case (e.g., strings.ToLower) before lookup or to store both cases in the map. [ Low confidence ]pkg/payerreport/workers/submitter.go — 0 comments posted, 4 evaluated, 4 filtered
report.AttestationSignaturescompared to a majority threshold derived fromlen(report.ActiveNodeIDs), without enforcing uniqueness or validating that those signatures correspond to distinct active approvers. This can allow duplicated or non-distinct signatures (or signatures from non-active nodes) to satisfy the threshold, incorrectly submitting a report without a true majority approval. Specifically, the logic atrequiredAttestations := (len(report.ActiveNodeIDs) / 2) + 1andif len(report.AttestationSignatures) < requiredAttestations { continue }fails to: (a) ensure signatures map to unique approver identities, (b) verify that approvers are members ofActiveNodeIDs, and (c) prevent duplicates. This violates the majority approval invariant and can result in on-chain submission under insufficient or invalid attestation. [ Low confidence ]IsErrPayerReportAlreadySubmitted()branch, failure ofSetReportSubmittedassignslatestErr = err, but in the successfulsubmitErr == nilbranch, failure ofSetReportSubmittedis only logged as a warning and not recorded inlatestErr. This asymmetry can lead toSubmitReportsreturningnileven when a state update failed in the success path, while similar failures in another branch are surfaced. Such inconsistency can surprise callers and complicate monitoring. [ Low confidence ]SetReportSubmittedcallingsetReportSubmissionStatuswith allowed-from[]SubmissionStatus{SubmissionPending}only) contradicts this. If the report is already inSubmissionSubmitted(e.g., set by the indexer), callingSetReportSubmittedwill likely fail due to the status transition guard. In the successfulsubmitErr == nilpath, this failure is merely warned and ignored, which directly contradicts the comment asserting that the function should handle the race. This documentation vs implementation mismatch creates uncertainty and can mask state update failures. [ Low confidence ]submitErr == nil), the code callsw.payerReportStore.SetReportSubmitted(ctx, report.ID)and only logs a warning when it fails, without updatinglatestError otherwise signaling the failure to the caller. This silently swallows a state update failure and causesSubmitReportsto returnnileven when the store did not persist theSubmittedstatus. This is inconsistent with the handling in theIsErrPayerReportAlreadySubmitted()branch, where a failure to set the submitted status assignslatestErr = err. The silent swallow at success path means the external caller may think submission completed cleanly while the database state remains stale, breaking contract parity for error propagation. [ Low confidence ]