Invalid Record: Plug wallet requestTransferToken call

Hi,
I am currently trying to invoke Plug Wallet to transfer tokens from code. I am following the code examples available in plug documentation. But i am having trouble figuring out, what exact argument types should be.
I am getting this error when trying to transfer, i have tried with requestTransferToken, directly calling icrc1_transfer via actor, also tried batching the transaction, but i keep getting the error shown below.
I have tried different iterations with different data types as well, but still unable to figure out what i am doing wrong.

const args = {
          to: {
            owner: Principal.fromText(receiverAccountId),
            subaccount: null
          },
          memo: null,
          fee: BigInt(10000),
          from_subaccount: null,
          created_at_time: null,
          amount: BigInt(100000)
        }
Error: Invalid record {to:record {owner:principal; subaccount:opt vec nat8}; fee:opt nat; memo:opt vec nat8; from_subaccount:opt vec nat8; created_at_time:opt nat64; amount:nat} argument: {"to":{"owner":{"__principal__":"nu3bp-ofgwc-agqjy-43yen-4746a-qwwq3-mcgj2-dj7hj-luvmp-gafkm-nae"},"subaccount":null},"memo":null,"fee":"BigInt(10000)","from_subaccount":null,"created_at_time":null,"amount":"BigInt(100000)"}

Hey,
i think since fee is optional you can just put it as null and it will be calculated automatically
this code worked for me try to change null to an empty array:

args: [
          to: {
            owner: Principal.fromText(receiverAccountId),
            subaccount: []
          },
          memo: null,
          fee: [],
          from_subaccount: [],
          created_at_time: [],
          amount: BigInt(100000)

This is the exact code that i am trying,

      const sonicTokenId = "qbizb-wiaaa-aaaaq-aabwq-cai";
      const hasAllowed = await window.ic.plug.requestConnect({
        whitelist: [sonicTokenId]
      });
      if (hasAllowed) {
        const actor = await window.ic.plug.createActor({
          canisterId: sonicTokenId,
          interfaceFactory: idlFactory
        });

        const receiverAccountId = 'nu3bp-ofgwc-agqjy-43yen-4746a-qwwq3-mcgj2-dj7hj-luvmp-gafkm-nae';

        const args = {
          to: {
            owner: Principal.fromText(receiverAccountId),
            subaccount: []
          },
          memo: null,
          fee: [],
          from_subaccount: [],
          created_at_time: [],
          amount: BigInt(100000)
        }

        const transfer = await actor.icrc1_transfer(args);
        console.log(transfer);

and used as you suggested, still got the same error

Error: Invalid record {to:record {owner:principal; subaccount:opt vec nat8}; fee:opt nat; memo:opt vec nat8; from_subaccount:opt vec nat8; created_at_time:opt nat64; amount:nat} argument: {"to":{"owner":{"__principal__":"nu3bp-ofgwc-agqjy-43yen-4746a-qwwq3-mcgj2-dj7hj-luvmp-gafkm-nae"},"subaccount":[]},"memo":null,"fee":[],"from_subaccount":[],"created_at_time":[],"amount":"BigInt(100000)"}
    at <anonymous>:97:20940
    at <anonymous>:97:3129
    at Array.map (<anonymous>)
    at l (<anonymous>:97:3117)
    at Module.T (<anonymous>:97:20900)
    at E.n (<anonymous>:5:4322)
    at p.i [as icrc1_transfer] (<anonymous>:5:4675)

Did you tried with plug wallet?

yes I’ve tried that with plug as well, pleas put memo as an empty array. I can see its still null in your code

Putting an empty array went through. thank you.
But i need to attach a memo to each transaction, i tried with memo: [1234], memo: [[1234]] with icrc1_transfer method. Also tried to use requestTransferToken from plug provider directly with ‘string’ memo value. all three cases resulted in same ‘Invalid Record’ error, any ideas?

Two examples of memo

memo: new Array(32).fill(0),
memo: RandomBigInt(32),

depending on your needs modify it

i tried with both, still the same issue :frowning:

Tagging @mzibara! He’s a great resource for anything technical related to Plug.

1 Like

Just following up if you ever figured this out!

hi thank you for following up. I couldn’t find any solution for this, and have parked it for now, its a blocker for me.

This may work.


export function convertToMemo(memo: number): number[] {
  let b = new ArrayBuffer(32);
  new DataView(b).setUint32(0, memo);
  return Array.from(new Uint8Array(b));
}

let args={
          to,
          fee: [],
          memo: [convertToMemo(34343)],
          from_subaccount: [ ],
          created_at_time: [],
          amount: 1000000n,
        }