mirror of
https://github.com/trezor/trezor-wallet
synced 2024-12-29 02:18:06 +00:00
Merge pull request #320 from trezor/fix/ripple-destination-tag
Fix/ripple destination tag
This commit is contained in:
commit
ba68fffc20
@ -70,7 +70,7 @@
|
|||||||
"rimraf": "^2.6.2",
|
"rimraf": "^2.6.2",
|
||||||
"styled-components": "^4.1.2",
|
"styled-components": "^4.1.2",
|
||||||
"styled-normalize": "^8.0.4",
|
"styled-normalize": "^8.0.4",
|
||||||
"trezor-connect": "7.0.0-beta.1",
|
"trezor-connect": "7.0.0-beta.2",
|
||||||
"wallet-address-validator": "^0.2.4",
|
"wallet-address-validator": "^0.2.4",
|
||||||
"web3": "1.0.0-beta.35",
|
"web3": "1.0.0-beta.35",
|
||||||
"webpack": "^4.16.3",
|
"webpack": "^4.16.3",
|
||||||
|
@ -118,7 +118,7 @@ export const onNotification = (payload: $ElementType<BlockchainNotification, 'pa
|
|||||||
|
|
||||||
const updatedAccount = await TrezorConnect.rippleGetAccountInfo({
|
const updatedAccount = await TrezorConnect.rippleGetAccountInfo({
|
||||||
account: {
|
account: {
|
||||||
address: account.descriptor,
|
descriptor: account.descriptor,
|
||||||
from: account.block,
|
from: account.block,
|
||||||
history: false,
|
history: false,
|
||||||
},
|
},
|
||||||
|
@ -76,6 +76,7 @@ export const discoverAccount = (device: TrezorDevice, discoveryProcess: Discover
|
|||||||
|
|
||||||
networkType: 'ripple',
|
networkType: 'ripple',
|
||||||
sequence: account.sequence,
|
sequence: account.sequence,
|
||||||
reserve: '0',
|
reserve: toDecimalAmount(account.reserve, network.decimals),
|
||||||
|
// reserve: '20',
|
||||||
};
|
};
|
||||||
};
|
};
|
@ -244,6 +244,23 @@ export const onFeeChange = (fee: string): ThunkAction => (dispatch: Dispatch, ge
|
|||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Called from UI on "advanced / destination tag" field change
|
||||||
|
*/
|
||||||
|
export const onDestinationTagChange = (destinationTag: string): ThunkAction => (dispatch: Dispatch, getState: GetState): void => {
|
||||||
|
const state: State = getState().sendFormRipple;
|
||||||
|
dispatch({
|
||||||
|
type: SEND.CHANGE,
|
||||||
|
networkType: 'ripple',
|
||||||
|
state: {
|
||||||
|
...state,
|
||||||
|
untouched: false,
|
||||||
|
touched: { ...state.touched, destinationTag: true },
|
||||||
|
destinationTag,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Called from UI from "send" button
|
* Called from UI from "send" button
|
||||||
*/
|
*/
|
||||||
@ -262,7 +279,13 @@ export const onSend = (): AsyncAction => async (dispatch: Dispatch, getState: Ge
|
|||||||
if (!blockchain) return;
|
if (!blockchain) return;
|
||||||
|
|
||||||
const currentState: State = getState().sendFormRipple;
|
const currentState: State = getState().sendFormRipple;
|
||||||
const amount = fromDecimalAmount(currentState.amount, 6);
|
const payment: { amount: string, destination: string, destinationTag?: number } = {
|
||||||
|
amount: fromDecimalAmount(currentState.amount, network.decimals),
|
||||||
|
destination: currentState.address,
|
||||||
|
};
|
||||||
|
if (currentState.destinationTag.length > 0) {
|
||||||
|
payment.destinationTag = parseInt(currentState.destinationTag, 10);
|
||||||
|
}
|
||||||
|
|
||||||
const signedTransaction = await TrezorConnect.rippleSignTransaction({
|
const signedTransaction = await TrezorConnect.rippleSignTransaction({
|
||||||
device: {
|
device: {
|
||||||
@ -276,10 +299,7 @@ export const onSend = (): AsyncAction => async (dispatch: Dispatch, getState: Ge
|
|||||||
fee: currentState.selectedFeeLevel.fee, // Fee must be in the range of 10 to 10,000 drops
|
fee: currentState.selectedFeeLevel.fee, // Fee must be in the range of 10 to 10,000 drops
|
||||||
flags: 0x80000000,
|
flags: 0x80000000,
|
||||||
sequence: account.sequence,
|
sequence: account.sequence,
|
||||||
payment: {
|
payment,
|
||||||
amount,
|
|
||||||
destination: currentState.address,
|
|
||||||
},
|
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -346,5 +366,6 @@ export default {
|
|||||||
onFeeLevelChange,
|
onFeeLevelChange,
|
||||||
updateFeeLevels,
|
updateFeeLevels,
|
||||||
onFeeChange,
|
onFeeChange,
|
||||||
|
onDestinationTagChange,
|
||||||
onSend,
|
onSend,
|
||||||
};
|
};
|
@ -73,6 +73,7 @@ export const validation = (): PayloadAction<State> => (dispatch: Dispatch, getSt
|
|||||||
state = dispatch(addressLabel(state));
|
state = dispatch(addressLabel(state));
|
||||||
state = dispatch(amountValidation(state));
|
state = dispatch(amountValidation(state));
|
||||||
state = dispatch(feeValidation(state));
|
state = dispatch(feeValidation(state));
|
||||||
|
state = dispatch(destinationTagValidation(state));
|
||||||
return state;
|
return state;
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -229,6 +230,19 @@ export const feeValidation = ($state: State): PayloadAction<State> => (dispatch:
|
|||||||
}
|
}
|
||||||
return state;
|
return state;
|
||||||
};
|
};
|
||||||
|
/*
|
||||||
|
* Destination Tag value validation
|
||||||
|
*/
|
||||||
|
export const destinationTagValidation = ($state: State): PayloadAction<State> => (): State => {
|
||||||
|
const state = { ...$state };
|
||||||
|
if (!state.touched.destinationTag) return state;
|
||||||
|
|
||||||
|
const { destinationTag } = state;
|
||||||
|
if (destinationTag.length > 0 && !destinationTag.match(ABS_RE)) {
|
||||||
|
state.errors.destinationTag = 'Destination tag must be an absolute number';
|
||||||
|
}
|
||||||
|
return state;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -27,6 +27,7 @@ export type State = {
|
|||||||
fee: string;
|
fee: string;
|
||||||
feeNeedsUpdate: boolean;
|
feeNeedsUpdate: boolean;
|
||||||
sequence: string;
|
sequence: string;
|
||||||
|
destinationTag: string;
|
||||||
total: string;
|
total: string;
|
||||||
|
|
||||||
errors: {[k: string]: string};
|
errors: {[k: string]: string};
|
||||||
@ -56,6 +57,7 @@ export const initialState: State = {
|
|||||||
fee: '0',
|
fee: '0',
|
||||||
feeNeedsUpdate: false,
|
feeNeedsUpdate: false,
|
||||||
sequence: '0',
|
sequence: '0',
|
||||||
|
destinationTag: '',
|
||||||
total: '0',
|
total: '0',
|
||||||
|
|
||||||
errors: {},
|
errors: {},
|
||||||
|
@ -95,6 +95,7 @@ export const getPendingSequence = (pending: Array<Transaction>): number => pendi
|
|||||||
}, 0);
|
}, 0);
|
||||||
|
|
||||||
export const getPendingAmount = (pending: Array<Transaction>, currency: string, token: boolean = false): BigNumber => pending.reduce((value: BigNumber, tx: Transaction): BigNumber => {
|
export const getPendingAmount = (pending: Array<Transaction>, currency: string, token: boolean = false): BigNumber => pending.reduce((value: BigNumber, tx: Transaction): BigNumber => {
|
||||||
|
if (tx.type !== 'send') return value;
|
||||||
if (!token) {
|
if (!token) {
|
||||||
// regular transactions
|
// regular transactions
|
||||||
// add fees from token txs and amount from regular txs
|
// add fees from token txs and amount from regular txs
|
||||||
|
@ -35,7 +35,7 @@ const AdvancedSettingsWrapper = styled.div`
|
|||||||
border-top: 1px solid ${colors.DIVIDER};
|
border-top: 1px solid ${colors.DIVIDER};
|
||||||
`;
|
`;
|
||||||
|
|
||||||
const GasInputRow = styled.div`
|
const InputRow = styled.div`
|
||||||
width: 100%;
|
width: 100%;
|
||||||
display: flex;
|
display: flex;
|
||||||
|
|
||||||
@ -44,7 +44,7 @@ const GasInputRow = styled.div`
|
|||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
|
|
||||||
const GasInput = styled(Input)`
|
const StyledInput = styled(Input)`
|
||||||
/* min-height: 85px; */
|
/* min-height: 85px; */
|
||||||
padding-bottom: 28px;
|
padding-bottom: 28px;
|
||||||
&:first-child {
|
&:first-child {
|
||||||
@ -75,6 +75,17 @@ const getFeeInputState = (feeErrors: string, feeWarnings: string): string => {
|
|||||||
return state;
|
return state;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const getDestinationTagInputState = (errors: string, warnings: string): string => {
|
||||||
|
let state = '';
|
||||||
|
if (warnings && !errors) {
|
||||||
|
state = 'warning';
|
||||||
|
}
|
||||||
|
if (errors) {
|
||||||
|
state = 'error';
|
||||||
|
}
|
||||||
|
return state;
|
||||||
|
};
|
||||||
|
|
||||||
const Left = styled.div`
|
const Left = styled.div`
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
@ -91,15 +102,17 @@ const AdvancedForm = (props: Props) => {
|
|||||||
warnings,
|
warnings,
|
||||||
infos,
|
infos,
|
||||||
fee,
|
fee,
|
||||||
|
destinationTag,
|
||||||
} = props.sendForm;
|
} = props.sendForm;
|
||||||
const {
|
const {
|
||||||
onFeeChange,
|
onFeeChange,
|
||||||
|
onDestinationTagChange,
|
||||||
} = props.sendFormActions;
|
} = props.sendFormActions;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<AdvancedSettingsWrapper>
|
<AdvancedSettingsWrapper>
|
||||||
<GasInputRow>
|
<InputRow>
|
||||||
<GasInput
|
<StyledInput
|
||||||
state={getFeeInputState(errors.fee, warnings.fee)}
|
state={getFeeInputState(errors.fee, warnings.fee)}
|
||||||
autoComplete="off"
|
autoComplete="off"
|
||||||
autoCorrect="off"
|
autoCorrect="off"
|
||||||
@ -115,7 +128,7 @@ const AdvancedForm = (props: Props) => {
|
|||||||
Transfer cost in XRP drops
|
Transfer cost in XRP drops
|
||||||
</React.Fragment>
|
</React.Fragment>
|
||||||
)}
|
)}
|
||||||
maxWidth={410}
|
maxWidth={100}
|
||||||
readMoreLink="https://developers.ripple.com/transaction-cost.html"
|
readMoreLink="https://developers.ripple.com/transaction-cost.html"
|
||||||
placement="top"
|
placement="top"
|
||||||
>
|
>
|
||||||
@ -132,7 +145,43 @@ const AdvancedForm = (props: Props) => {
|
|||||||
value={fee}
|
value={fee}
|
||||||
onChange={event => onFeeChange(event.target.value)}
|
onChange={event => onFeeChange(event.target.value)}
|
||||||
/>
|
/>
|
||||||
</GasInputRow>
|
</InputRow>
|
||||||
|
|
||||||
|
<InputRow>
|
||||||
|
<StyledInput
|
||||||
|
state={getDestinationTagInputState(errors.destinationTag, warnings.destinationTag)}
|
||||||
|
autoComplete="off"
|
||||||
|
autoCorrect="off"
|
||||||
|
autoCapitalize="off"
|
||||||
|
spellCheck="false"
|
||||||
|
topLabel={(
|
||||||
|
<InputLabelWrapper>
|
||||||
|
<Left>
|
||||||
|
Destination tag
|
||||||
|
<Tooltip
|
||||||
|
content={(
|
||||||
|
<React.Fragment>
|
||||||
|
An arbitrary unsigned 32-bit integer that identifies a reason for payment or a non-Ripple account.
|
||||||
|
</React.Fragment>
|
||||||
|
)}
|
||||||
|
maxWidth={200}
|
||||||
|
readMoreLink="https://developers.ripple.com/rippleapi-reference.html#payment"
|
||||||
|
placement="top"
|
||||||
|
>
|
||||||
|
<Icon
|
||||||
|
icon={ICONS.HELP}
|
||||||
|
color={colors.TEXT_SECONDARY}
|
||||||
|
size={24}
|
||||||
|
/>
|
||||||
|
</Tooltip>
|
||||||
|
</Left>
|
||||||
|
</InputLabelWrapper>
|
||||||
|
)}
|
||||||
|
bottomText={errors.destinationTag || warnings.destinationTag || infos.destinationTag}
|
||||||
|
value={destinationTag}
|
||||||
|
onChange={event => onDestinationTagChange(event.target.value)}
|
||||||
|
/>
|
||||||
|
</InputRow>
|
||||||
|
|
||||||
<AdvancedSettingsSendButtonWrapper>
|
<AdvancedSettingsSendButtonWrapper>
|
||||||
{ props.children }
|
{ props.children }
|
||||||
|
@ -9790,9 +9790,9 @@ tr46@^1.0.1:
|
|||||||
dependencies:
|
dependencies:
|
||||||
punycode "^2.1.0"
|
punycode "^2.1.0"
|
||||||
|
|
||||||
trezor-connect@7.0.0-beta.1:
|
trezor-connect@7.0.0-beta.2:
|
||||||
version "7.0.0-beta.1"
|
version "7.0.0-beta.2"
|
||||||
resolved "https://registry.yarnpkg.com/trezor-connect/-/trezor-connect-7.0.0-beta.1.tgz#de87d8f1d9878101380f7b3198bf2531d7560a5c"
|
resolved "https://registry.yarnpkg.com/trezor-connect/-/trezor-connect-7.0.0-beta.2.tgz#10dc04e1b60804263e9873cd503a4fc9d3e940d2"
|
||||||
dependencies:
|
dependencies:
|
||||||
babel-runtime "^6.26.0"
|
babel-runtime "^6.26.0"
|
||||||
events "^1.1.1"
|
events "^1.1.1"
|
||||||
|
Loading…
Reference in New Issue
Block a user