Skip to content
This repository has been archived by the owner on Jul 15, 2022. It is now read-only.

Commit

Permalink
Filecoin fixes (#1740)
Browse files Browse the repository at this point in the history
* make use of useAllAmount flag

* make use of useAllAmount on signing tx process

* refactor signOperation process to use extra field better

* add deviceTransactionConfig for filecoin

* re org fields for confirm tx

* change fields order

* add extra field parsers

* move extra field parsers to the correct file

* fix lint issue
  • Loading branch information
emmanuelm41 authored and hakim-adamik committed Mar 9, 2022
1 parent 5cd89e6 commit c150236
Show file tree
Hide file tree
Showing 8 changed files with 192 additions and 35 deletions.
44 changes: 44 additions & 0 deletions src/families/filecoin/account.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
import BigNumber from "bignumber.js";

export function fromOperationExtraRaw(
extra: Record<string, any> | null | undefined
): Record<string, any> | null | undefined {
if (!extra) return extra;

const { gasLimit, gasPremium, gasFeeCap } = extra;

if (gasLimit !== undefined)
extra = { ...extra, gasLimit: new BigNumber(gasLimit) };

if (gasPremium !== undefined)
extra = { ...extra, gasPremium: new BigNumber(gasPremium) };

if (gasFeeCap !== undefined)
extra = { ...extra, gasFeeCap: new BigNumber(gasFeeCap) };

return extra;
}

export function toOperationExtraRaw(
extra: Record<string, any> | null | undefined
): Record<string, any> | null | undefined {
if (!extra) return extra;

const { gasLimit, gasPremium, gasFeeCap } = extra;

if (gasLimit !== undefined)
extra = { ...extra, gasLimit: gasLimit.toNumber() };

if (gasPremium !== undefined)
extra = { ...extra, gasPremium: gasPremium.toFixed() };

if (gasFeeCap !== undefined)
extra = { ...extra, gasFeeCap: gasFeeCap.toFixed() };

return extra;
}

export default {
fromOperationExtraRaw,
toOperationExtraRaw,
};
52 changes: 34 additions & 18 deletions src/families/filecoin/bridge/account.ts
Original file line number Diff line number Diff line change
Expand Up @@ -66,8 +66,10 @@ const getTransactionStatus = async (
const errors: TransactionStatus["errors"] = {};
const warnings: TransactionStatus["warnings"] = {};

const { balance } = a;
const { address } = getAddress(a);
const { recipient, amount, gasPremium, gasFeeCap, gasLimit } = t;
const { recipient, useAllAmount, gasPremium, gasFeeCap, gasLimit } = t;
let { amount } = t;

if (!recipient) errors.recipient = new RecipientRequired();
else if (!validateAddress(recipient).isValid)
Expand All @@ -81,8 +83,8 @@ const getTransactionStatus = async (
// This is the worst case scenario (the tx won't cost more than this value)
const estimatedFees = calculateEstimatedFees(gasFeeCap, gasLimit);

// Add the estimated fees to the tx amount
const totalSpent = amount.plus(estimatedFees);
const totalSpent = useAllAmount ? balance : amount.plus(estimatedFees);
amount = useAllAmount ? balance.minus(estimatedFees) : amount;

if (amount.lte(0)) errors.amount = new AmountRequired();
if (totalSpent.gt(a.spendableBalance)) errors.amount = new NotEnoughBalance();
Expand Down Expand Up @@ -174,11 +176,13 @@ const prepareTransaction = async (
const sync = makeSync(getAccountShape);

const broadcast: BroadcastFnSignature = async ({
signedOperation: { operation },
signedOperation: { operation, signature },
}) => {
// log("debug", "[broadcast] start fn");

const resp = await broadcastTx(operation.extra.reqToBroadcast);
const tx = getTxToBroadcast(operation, signature);

const resp = await broadcastTx(tx);
const { hash } = resp;

const result = patchOperationWithHash(operation, hash);
Expand All @@ -199,8 +203,18 @@ const signOperation: SignOperationFnSignature<Transaction> = ({
async function main() {
// log("debug", "[signOperation] start fn");

const { recipient, amount, gasFeeCap, gasLimit } = transaction;
const { id: accountId } = account;
const {
recipient,
method,
version,
nonce,
gasFeeCap,
gasLimit,
gasPremium,
useAllAmount,
} = transaction;
let { amount } = transaction;
const { id: accountId, balance } = account;
const { address, derivationPath } = getAddress(account);

if (!gasFeeCap.gt(0) || !gasLimit.gt(0)) {
Expand All @@ -218,6 +232,11 @@ const signOperation: SignOperationFnSignature<Transaction> = ({
type: "device-signature-requested",
});

const fee = calculateEstimatedFees(gasFeeCap, gasLimit);
if (useAllAmount) amount = balance.minus(fee);

transaction = { ...transaction, amount };

// Serialize tx
const serializedTx = toCBOR(
getAddressRaw(address),
Expand All @@ -243,35 +262,32 @@ const signOperation: SignOperationFnSignature<Transaction> = ({
type: "device-signature-granted",
});

const fee = calculateEstimatedFees(gasFeeCap, gasLimit);
const value = amount.plus(fee);

// resolved at broadcast time
const txHash = "";

// build signature on the correct format
const signature = `${result.signature_compact.toString("base64")}`;

const reqToBroadcast = getTxToBroadcast(
account,
transaction,
signature
);

const operation: Operation = {
id: `${accountId}-${txHash}-OUT`,
hash: txHash,
type: "OUT",
senders: [address],
recipients: [recipient],
accountId,
value,
value: amount,
fee,
blockHash: null,
blockHeight: null,
date: new Date(),
extra: {
reqToBroadcast,
gasLimit,
gasFeeCap,
gasPremium,
method,
version,
nonce,
signatureType: 1,
},
};

Expand Down
19 changes: 8 additions & 11 deletions src/families/filecoin/bridge/utils/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@ import {
import { fetchBalances, fetchBlockHeight, fetchTxs } from "./api";
import { encodeAccountId } from "../../../../account";
import flatMap from "lodash/flatMap";
import { Transaction } from "../../types";

type TxsById = {
[id: string]: {
Expand Down Expand Up @@ -103,37 +102,35 @@ export const getAddress = (a: Account): Address =>
: { address: a.freshAddress, derivationPath: a.freshAddressPath };

export const getTxToBroadcast = (
account: Account,
transaction: Transaction,
operation: Operation,
signature: string
): BroadcastTransactionRequest => {
const { address } = getAddress(account);
const { extra, senders, recipients, value } = operation;
const {
recipient,
amount,
gasLimit,
gasFeeCap,
gasPremium,
method,
version,
nonce,
} = transaction;
signatureType,
} = extra;

return {
message: {
version,
method,
nonce,
params: "",
to: recipient,
from: address,
to: recipients[0],
from: senders[0],
gaslimit: gasLimit.toNumber(),
gaspremium: gasPremium.toString(),
gasfeecap: gasFeeCap.toString(),
value: amount.toFixed(),
value: value.toFixed(),
},
signature: {
type: 1,
type: signatureType,
data: signature,
},
};
Expand Down
73 changes: 73 additions & 0 deletions src/families/filecoin/deviceTransactionConfig.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
import type { DeviceTransactionField } from "../../transaction";
import type { Account, AccountLike, TransactionStatus } from "../../types";
import type { Transaction } from "./types";
import { formatCurrencyUnit, getCryptoCurrencyById } from "../../currencies";
import { methodToString } from "./utils";

const currency = getCryptoCurrencyById("filecoin");

export type ExtraDeviceTransactionField =
| {
type: "filecoin.gasFeeCap";
label: string;
value: string;
}
| {
type: "filecoin.gasPremium";
label: string;
value: string;
}
| {
type: "filecoin.gasLimit";
label: string;
value: string;
}
| {
type: "filecoin.method";
label: string;
value: string;
};

function getDeviceTransactionConfig(input: {
account: AccountLike;
parentAccount: Account | null | undefined;
transaction: Transaction;
status: TransactionStatus;
}): Array<DeviceTransactionField> {
const fields: Array<DeviceTransactionField> = [];

fields.push({
type: "amount",
label: "Value",
});
fields.push({
type: "filecoin.gasLimit",
label: "Gas Limit",
value: input.transaction.gasLimit.toFixed(),
});
fields.push({
type: "filecoin.gasPremium",
label: "Gas Premium",
value: formatCurrencyUnit(currency.units[0], input.transaction.gasPremium, {
showCode: false,
disableRounding: true,
}),
});
fields.push({
type: "filecoin.gasFeeCap",
label: "Gas Fee Cap",
value: formatCurrencyUnit(currency.units[0], input.transaction.gasFeeCap, {
showCode: false,
disableRounding: true,
}),
});
fields.push({
type: "filecoin.method",
label: "Method",
value: methodToString(input.transaction.method),
});

return fields;
}

export default getDeviceTransactionConfig;
22 changes: 16 additions & 6 deletions src/families/filecoin/transaction.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,22 @@ import { getAccountUnit } from "../../account";
import { formatCurrencyUnit } from "../../currencies";
import BigNumber from "bignumber.js";

export const formatTransaction = (t: Transaction, account: Account): string => `
SEND ${formatCurrencyUnit(getAccountUnit(account), t.amount, {
showCode: true,
disableRounding: true,
})}
TO ${t.recipient}`;
export const formatTransaction = (
{ recipient, useAllAmount, amount }: Transaction,
account: Account
): string => `
SEND ${
useAllAmount
? "MAX"
: amount.isZero()
? ""
: " " +
formatCurrencyUnit(getAccountUnit(account), amount, {
showCode: true,
disableRounding: true,
})
}
TO ${recipient}`;

export const fromTransactionRaw = (tr: TransactionRaw): Transaction => {
const common = fromTransactionCommonRaw(tr);
Expand Down
9 changes: 9 additions & 0 deletions src/families/filecoin/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,15 @@ export const isError = (r: { return_code: number; error_message: string }) => {
throw new Error(`${r.return_code} - ${r.error_message}`);
};

export const methodToString = (method: number): string => {
switch (method) {
case 0:
return "Transfer";
default:
return "Unknown";
}
};

export const getBufferFromString = (message: string): Buffer =>
isValidHex(message)
? Buffer.from(message, "hex")
Expand Down
3 changes: 3 additions & 0 deletions src/generated/account.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ import crypto_org from "../families/crypto_org/account";

import elrond from "../families/elrond/account";

import filecoin from "../families/filecoin/account";

import polkadot from "../families/polkadot/account";


Expand All @@ -17,5 +19,6 @@ export default {
cosmos,
crypto_org,
elrond,
filecoin,
polkadot,
};
5 changes: 5 additions & 0 deletions src/generated/deviceTransactionConfig.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@ import elrond from "../families/elrond/deviceTransactionConfig";

import ethereum from "../families/ethereum/deviceTransactionConfig";

import filecoin from "../families/filecoin/deviceTransactionConfig";

import polkadot from "../families/polkadot/deviceTransactionConfig";

import ripple from "../families/ripple/deviceTransactionConfig";
Expand All @@ -33,6 +35,7 @@ export default {
crypto_org,
elrond,
ethereum,
filecoin,
polkadot,
ripple,
solana,
Expand All @@ -41,12 +44,14 @@ export default {
tron,
};
import { ExtraDeviceTransactionField as ExtraDeviceTransactionField_cosmos } from "../families/cosmos/deviceTransactionConfig";
import { ExtraDeviceTransactionField as ExtraDeviceTransactionField_filecoin } from "../families/filecoin/deviceTransactionConfig";
import { ExtraDeviceTransactionField as ExtraDeviceTransactionField_polkadot } from "../families/polkadot/deviceTransactionConfig";
import { ExtraDeviceTransactionField as ExtraDeviceTransactionField_stellar } from "../families/stellar/deviceTransactionConfig";
import { ExtraDeviceTransactionField as ExtraDeviceTransactionField_tezos } from "../families/tezos/deviceTransactionConfig";
import { ExtraDeviceTransactionField as ExtraDeviceTransactionField_tron } from "../families/tron/deviceTransactionConfig";
export type ExtraDeviceTransactionField =
| ExtraDeviceTransactionField_cosmos
| ExtraDeviceTransactionField_filecoin
| ExtraDeviceTransactionField_polkadot
| ExtraDeviceTransactionField_stellar
| ExtraDeviceTransactionField_tezos
Expand Down

0 comments on commit c150236

Please sign in to comment.