Repository: wevm/viem (TypeScript)

Issue:
decodeEventLog in strict: true mode fails to enforce ABI conformity on indexed arguments
### Is there an existing issue for this?

- [X] I have searched the existing issues

### Package Version

^1.15.1

### Current Behavior

I've encountered an issue where `decodeEventLog` when used with `strict: true` is not enforcing the ABI conformity regarding the number of indexed arguments. According to the documentation, strict: true should throw an error when there's a mismatch between the number of indexed/non-indexed arguments and the data length. However, it seems to be allowing partial decoding without throwing an error when there's a mismatch, especially concerning the indexed argument `nounId` in the `AuctionCreated` event.

`decodeEventLog` with `strict: true` allows partial decoding of the `AuctionCreated` event, missing the indexed nounId argument, without throwing an error.



### Expected Behavior

`decodeEventLog` with `strict: true` should either throw an error due to a mismatch or correctly decode all arguments, including indexed arguments like nounId.



### Steps To Reproduce

Use decodeEventLog with strict: true to decode the AuctionCreated event from the following transaction: [Etherscan Transaction](https://etherscan.io/tx/0xb4b02bd9f1df0fbddd91a694b9b20b7656656a713f216dec6bdfb474e4d41fb2#eventlog)


Observe that nounId is missing from the decoded event, and no error is thrown for the mismatch.

`const decoded = decodeEventLog({
  abi,
  data,
  strict: true,
  eventName,
  topics,
});

// Output missing `nounId`, no error thrown
`

### Link to Minimal Reproducible Example (StackBlitz, CodeSandbox, GitHub repo etc.)

_No response_

### Anything else?

The documentation mentions that setting strict: false should allow for partial decoding, but strict: true should enforce strict ABI conformity and throw an error on mismatch. The current behavior deviates from this expectation.


Discussion: I might just misunderstand how indexed args are supposed to behave, in which case feel free to close :) 
What’s your ABI?
NounsAuctionHouse https://etherscan.io/address/0xf15a943787014461d94da08ad4040f79cd7c124e#code
Nice catch! PR here: https://github.com/wagmi-dev/viem/pull/1339



Fix (patch):
diff --git a/.changeset/plenty-meals-visit.md b/.changeset/plenty-meals-visit.md
new file mode 100644
index 0000000000..462ae4137e
--- /dev/null
+++ b/.changeset/plenty-meals-visit.md
@@ -0,0 +1,5 @@
+---
+"viem": patch
+---
+
+Fixed topics mismatch in `decodeEventLogs` strict mode.
diff --git a/src/utils/abi/decodeEventLog.ts b/src/utils/abi/decodeEventLog.ts
index 43c5388950..672c49017f 100644
--- a/src/utils/abi/decodeEventLog.ts
+++ b/src/utils/abi/decodeEventLog.ts
@@ -124,17 +124,15 @@ export function decodeEventLog<
 
   // Decode topics (indexed args).
   const indexedInputs = inputs.filter((x) => 'indexed' in x && x.indexed)
-  if (argTopics.length > 0) {
-    for (let i = 0; i < indexedInputs.length; i++) {
-      const param = indexedInputs[i]
-      const topic = argTopics[i]
-      if (!topic)
-        throw new DecodeLogTopicsMismatch({
-          abiItem,
-          param: param as AbiParameter & { indexed: boolean },
-        })
-      args[param.name || i] = decodeTopic({ param, value: topic })
-    }
+  for (let i = 0; i < indexedInputs.length; i++) {
+    const param = indexedInputs[i]
+    const topic = argTopics[i]
+    if (!topic)
+      throw new DecodeLogTopicsMismatch({
+        abiItem,
+        param: param as AbiParameter & { indexed: boolean },
+      })
+    args[param.name || i] = decodeTopic({ param, value: topic })
   }
 
   // Decode data (non-indexed args).