Across
Across is a bridge protocol, so the parser focuses on identifying BRIDGE_OUT
and BRIDGE_IN
actions from its on-chain events.
🧩 Files Involved in the Across Parser
src/lib/Across/
├── abis/SpokePool.json ← Only needed ABI fragments
├── contracts.ts ← Address + event signature map
├── parser.ts ← Logic to build actions from tx logs
└── index.ts ← Parser class exposed to the framework
1. contracts.ts
— Contract Definitions & Event Signatures
contracts.ts
— Contract Definitions & Event SignaturesThis file defines which contracts Across uses on each chain, and how to identify the logs they emit.
export enum ACROSS_CONTRACTS {
SPOKE_POOL = "SPOKE_POOL"
}
export const acrossContracts: IProtocolContractDefinitions = {
[CHAIN_ID.ETHEREUM]: {
[ACROSS_CONTRACTS.SPOKE_POOL]: {
address: "0x...", // SpokePool address on Ethereum
listener: LISTEN_FOR_TRANSACTIONS.TO,
abi: SpokePoolABI,
events: {
FilledRelay: "FilledRelay(address,address,address,uint256,uint256,uint256,bool,bytes32)",
Deposited: "Deposited(address,address,address,uint256,uint256,uint256,bytes32)"
}
}
},
...
};
Here we:
Define what contract to listen to (e.g.
SpokePool
)Where to listen (
to
orfrom
in tx)Which events (logs) we care about
2. parser.ts
— Parsing the Logs into Actions
parser.ts
— Parsing the Logs into Actionsexport const parseAcrossTx = (tx: ITransaction, helper: ProtocolHelper): ITransactionAction[] => {
const actions: ITransactionAction[] = [];
for (const log of tx.logs) {
const parsed = helper.parseLog(log);
if (!parsed) continue;
const { name, args } = parsed;
if (name === "FilledRelay") {
actions.push({
action: ACTION_ENUM.BRIDGE_IN,
chainId: tx.chainId,
from: args.originToken,
to: args.destinationToken,
amount: args.amount,
userAddress: args.recipient,
txHash: tx.hash,
timestamp: tx.timestamp
});
}
if (name === "Deposited") {
actions.push({
action: ACTION_ENUM.BRIDGE_OUT,
chainId: tx.chainId,
from: args.originToken,
to: args.destinationToken,
amount: args.amount,
userAddress: args.depositor,
txHash: tx.hash,
timestamp: tx.timestamp
});
}
}
return actions;
};
🧠 Note:
It loops through logs, uses a helper to parse each log via ABI
Builds high-level
ITransactionAction
objectsEach action gets:
action
,chainId
,tokens
,user
,amount
,timestamp
3. index.ts
— The Parser Class
index.ts
— The Parser Classexport default class Across implements IProtocolParserExport {
readonly protocolIdentifier = "across";
parseTransaction(tx: ITransaction): ITransactionAction[] {
const helper = new ProtocolHelper(acrossContracts, tx);
if (!helper.txToAnyContract()) return [];
return parseAcrossTx(tx, helper);
}
getProtocolContracts() {
return acrossContracts;
}
}
This is the entry point used by the global parser map. It:
Uses
ProtocolHelper
to check if the tx is related to AcrossIf yes, passes it to
parseAcrossTx
Returns any
ITransactionAction
s it detects
Recap: How Across Parser Works
Contract Setup
Define SpokePool addresses and events in contracts.ts
Parsing Logic
Loop through logs and map to BRIDGE_IN
/ BRIDGE_OUT
Runtime Class
Implements IProtocolParserExport
to plug into SDK
Output
Returns typed ITransactionAction[]
used for OpenRep scoring
Last updated