dai.js icon indicating copy to clipboard operation
dai.js copied to clipboard

`transactionManager` doesn't track a transaction

Open valiafetisov opened this issue 4 years ago • 2 comments

Hello there! I am trying to use maker.service('transactionManager') according to the docs, by passing a transaction promise, but for some reason, it doesn't track anything at all or throw any error.

Sample code, that doesn't log anything in the console and never resolve the promise:

const collateralType = 'AAVE-A';
const auctionId = 2;
const walletAddress = 'your_wallet_address';

const clipperContract = maker.service('liquidation')._clipperContractByIlk(collateralType);
const transaction = clipperContract.redo(auctionId, walletAddress);

const transactionManager = maker.service('transactionManager');
await new Promise((resolve, reject): void => {
    transactionManager.listen(transaction, {
         pending: (tx: any) => {
            console.log('pending', tx);
        },
        mined: (tx: any) => {
            console.log('mined', tx);
        },
        confirmed: (tx: any) => {
            console.log('confirmed', tx);
            resolve(tx);
        },
        error: (tx: any) => {
            console.error('error', tx);
            const errorMessage = tx?.error?.message || 'unknown';
            reject(new Error(errorMessage));
        },
    });
    transactionManager.confirm(transaction);
});

Does transactionManager only track certain types of transactions? Or do I miss something?

valiafetisov avatar Oct 12 '21 12:10 valiafetisov

Hi @valiafetisov there's a couple of gotcha's here, you have to decorate the contract function with the @tracksTransactions decorator, and pass the promise there as well. Here's an example of that in the LiquidationService.

So in your case it would be the clipper.redo() function. You might need to move the reference to the contract inside a redo method on the LiquidationService. So a little bit of pseudo code using your example:

    ...

// move this call into a "redo" method on the LiquidationService:
// const clipperContract = maker.service('liquidation')._clipperContractByIlk(collateralType);

// const transaction = clipperContract.redo(auctionId, walletAddress);

const transaction = maker.service('liquidation').redo(auctionId, walletAddress);

const transactionManager = maker.service('transactionManager');
await new Promise((resolve, reject): void => {
    transactionManager.listen(transaction, {

    ...

b-pmcg avatar Oct 12 '21 15:10 b-pmcg

  1. Wouldn't it be desirable if transactionManager will throw an error if decorator is not present?
  2. Why do we actually need a decorator? Isn't transactionManager or at least its confirm method implements a generic polling functionality that only needs transaction hash to be able to check if it was mined or not?

Anyway, I made a PR https://github.com/makerdao/dai.js/pull/298 based on your suggestion, please have a look 🙂

valiafetisov avatar Oct 13 '21 09:10 valiafetisov