Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: issue limit order & add tracking #2289

Merged
merged 8 commits into from
Oct 12, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 7 additions & 4 deletions src/components/swapv2/LimitOrder/ActionButtonLimitOrder.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import {
} from 'components/Button'
import ProgressSteps from 'components/ProgressSteps'
import { RowBetween } from 'components/Row'
import { EditOrderInfo } from 'components/swapv2/LimitOrder/type'
import { useActiveWeb3React } from 'hooks'
import { ApprovalState } from 'hooks/useApproveCallback'
import { useWalletModalToggle } from 'state/application/hooks'
Expand All @@ -34,7 +35,7 @@ export default function ActionButtonLimitOrder({
approvalSubmitted,
showApproveFlow,
showWarning,
isEdit,
editOrderInfo,
}: {
currencyIn: Currency | undefined
currencyOut: Currency | undefined
Expand All @@ -52,11 +53,13 @@ export default function ActionButtonLimitOrder({
approveCallback: () => Promise<void>
onWrapToken: () => Promise<void>
showPreview: () => void
isEdit: boolean
editOrderInfo?: EditOrderInfo
}) {
const { isEdit, renderCancelButtons } = editOrderInfo || {}
const disableBtnApproved =
approval === ApprovalState.PENDING ||
((approval !== ApprovalState.NOT_APPROVED || approvalSubmitted || !!hasInputError) && enoughAllowance)
!!hasInputError ||
((approval !== ApprovalState.NOT_APPROVED || approvalSubmitted) && enoughAllowance)

const disableBtnReview =
checkingAllowance ||
Expand Down Expand Up @@ -115,7 +118,7 @@ export default function ActionButtonLimitOrder({
)

if (isEdit) {
return null
return checkingAllowance ? <ButtonPrimary disabled>{contentButton}</ButtonPrimary> : renderCancelButtons?.() || null
}

if (showWarning && !disableBtnReview) return <ButtonWarning onClick={showPreview}>{contentButton}</ButtonWarning>
Expand Down
9 changes: 5 additions & 4 deletions src/components/swapv2/LimitOrder/EditOrderModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,7 @@ export default function EditOrderModal({
)

const isSupportSoftCancelOrder = useIsSupportSoftCancelOrder()
const supportGasLessCancel = isSupportSoftCancelOrder(order)
const { orderSupportGasless: supportGasLessCancel, chainSupportGasless } = isSupportSoftCancelOrder(order)
const [cancelType, setCancelType] = useState(CancelOrderType.GAS_LESS_CANCEL)
useEffect(() => {
setCancelType(supportGasLessCancel ? CancelOrderType.GAS_LESS_CANCEL : CancelOrderType.HARD_CANCEL)
Expand All @@ -98,7 +98,6 @@ export default function EditOrderModal({

const estimateGas = useEstimateFee({ orders })

const editOrderInfo: EditOrderInfo = { isEdit: true, gasFee: estimateGas, cancelType }
const theme = useTheme()
const isReviewOrder = step === Steps.REVIEW_ORDER
const onBack = () => {
Expand Down Expand Up @@ -139,8 +138,10 @@ export default function EditOrderModal({
onDismiss={onDismiss}
onClickGaslessCancel={onClickGaslessCancel}
onClickHardCancel={onClickHardCancel}
order={order}
buttonInfo={{
supportGasLessCancel,
orderSupportGasless: supportGasLessCancel,
chainSupportGasless,
disabledGasLessCancel,
disabledHardCancel,
cancelGaslessText: <Trans>Gasless Edit</Trans>,
Expand All @@ -153,6 +154,7 @@ export default function EditOrderModal({
)
}

const editOrderInfo: EditOrderInfo = { isEdit: true, gasFee: estimateGas, cancelType, renderCancelButtons }
return (
<Modal isOpen={isOpen && !!currencyIn && !!currencyOut && !!defaultActiveMakingAmount} onDismiss={onDismiss}>
<Wrapper>
Expand Down Expand Up @@ -193,7 +195,6 @@ export default function EditOrderModal({
defaultExpire={defaultExpire}
/>
)}
{renderCancelButtons()}
</Wrapper>
</Modal>
)
Expand Down
55 changes: 32 additions & 23 deletions src/components/swapv2/LimitOrder/LimitOrderForm.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -583,7 +583,6 @@ const LimitOrderForm = forwardRef<LimitOrderFormHandle, Props>(function LimitOrd
!checkingAllowance &&
!showWrap &&
!isNotFillAllInput &&
!hasInputError &&
(approval === ApprovalState.NOT_APPROVED ||
approval === ApprovalState.PENDING ||
!enoughAllowance ||
Expand All @@ -601,13 +600,37 @@ const LimitOrderForm = forwardRef<LimitOrderFormHandle, Props>(function LimitOrd
hasChangedOrderInfo() {
return (
isEdit &&
!hasInputError &&
(defaultInputAmount !== inputAmount ||
defaultRate?.rate !== rateInfo.rate ||
defaultExpire?.getTime() !== expiredAt)
)
},
}))

const renderActionBtn = () => (
<ActionButtonLimitOrder
{...{
currencyIn,
currencyOut,
approval,
showWrap,
isWrappingEth,
isNotFillAllInput,
approvalSubmitted,
hasInputError,
enoughAllowance,
checkingAllowance,
wrapInputError,
approveCallback,
onWrapToken,
showPreview,
showApproveFlow,
showWarning: warningMessage.length > 0,
editOrderInfo,
}}
/>
)
const renderConfirmModal = (showConfirmContent = false) => (
<ConfirmOrderModal
flowState={flowState}
Expand All @@ -628,7 +651,13 @@ const LimitOrderForm = forwardRef<LimitOrderFormHandle, Props>(function LimitOrd
/>
)

if (isEdit && flowState.showConfirm) return renderConfirmModal(true)
if (isEdit && flowState.showConfirm)
return (
<>
{renderConfirmModal(true)}
{renderActionBtn()}
</>
)
return (
<>
<Flex flexDirection={'column'} style={{ gap: '1rem' }}>
Expand Down Expand Up @@ -779,27 +808,7 @@ const LimitOrderForm = forwardRef<LimitOrderFormHandle, Props>(function LimitOrd
<ErrorWarningPanel type="warn" key={i} title={mess} />
))}

<ActionButtonLimitOrder
{...{
currencyIn,
currencyOut,
approval,
showWrap,
isWrappingEth,
isNotFillAllInput,
approvalSubmitted,
hasInputError,
enoughAllowance,
checkingAllowance,
wrapInputError,
approveCallback,
onWrapToken,
showPreview,
showApproveFlow,
showWarning: warningMessage.length > 0,
isEdit,
}}
/>
{renderActionBtn()}
</Flex>

{renderConfirmModal()}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -219,19 +219,29 @@ export const useProcessCancelOrder = ({
getOrders: (v: boolean) => LimitOrder[]
isEdit?: boolean
}) => {
const { chainId } = useActiveWeb3React()
const [expiredTime, setExpiredTime] = useState(0)
const [cancelStatus, setCancelStatus] = useState<CancelStatus>(CancelStatus.WAITING)
const controller = useRef(new AbortController())

const onResetState = useCallback(() => {
setExpiredTime(0)
setCancelStatus(CancelStatus.WAITING)
}, [])

useEffect(() => {
if (!isOpen) {
setCancelStatus(CancelStatus.WAITING)
onResetState()
}
return () => {
controller?.current?.abort()
controller.current = new AbortController()
}
}, [isOpen])
}, [isOpen, onResetState])

useEffect(() => {
onResetState()
}, [chainId, onResetState])

const requestCancel = async (type: CancelOrderType) => {
const signal = controller.current.signal
Expand All @@ -246,6 +256,7 @@ export const useProcessCancelOrder = ({
else onDismiss()
} catch (error) {
if (signal.aborted) return
setExpiredTime(0)
setCancelStatus(expiredTime ? CancelStatus.COUNTDOWN : CancelStatus.WAITING)
}
}
Expand Down
38 changes: 32 additions & 6 deletions src/components/swapv2/LimitOrder/Modals/CancelButtons.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,10 @@ import { GasStation } from 'components/Icons'
import { MouseoverTooltip } from 'components/Tooltip'
import { CancelStatus } from 'components/swapv2/LimitOrder/Modals/CancelOrderModal'
import { DOCS_LINKS } from 'components/swapv2/LimitOrder/const'
import { CancelOrderType } from 'components/swapv2/LimitOrder/type'
import { getPayloadTracking } from 'components/swapv2/LimitOrder/helpers'
import { CancelOrderType, LimitOrder } from 'components/swapv2/LimitOrder/type'
import { useActiveWeb3React } from 'hooks'
import useMixpanel, { MIXPANEL_TYPE } from 'hooks/useMixpanel'
import useTheme from 'hooks/useTheme'
import { ExternalLink } from 'theme'
import { formatDisplayNumber } from 'utils/numbers'
Expand Down Expand Up @@ -73,7 +76,8 @@ const ButtonWrapper = styled.div`
`

type ButtonInfo = {
supportGasLessCancel: boolean
orderSupportGasless: boolean
chainSupportGasless: boolean
disabledGasLessCancel: boolean
disabledHardCancel: boolean
cancelGaslessText: ReactNode
Expand All @@ -93,8 +97,10 @@ const CancelButtons = ({
confirmOnly = false,
cancelType,
setCancelType,
order,
buttonInfo: {
supportGasLessCancel,
orderSupportGasless,
chainSupportGasless,
disabledGasLessCancel = false,
disabledHardCancel = false,
cancelGaslessText,
Expand All @@ -114,12 +120,26 @@ const CancelButtons = ({
cancelType: CancelOrderType
setCancelType: (v: CancelOrderType) => void
buttonInfo: ButtonInfo
order: LimitOrder | undefined
}) => {
const theme = useTheme()
const isWaiting = cancelStatus === CancelStatus.WAITING
const isCountDown = cancelStatus === CancelStatus.COUNTDOWN
const isTimeout = cancelStatus === CancelStatus.TIMEOUT
const isCancelDone = cancelStatus === CancelStatus.CANCEL_DONE
const { mixpanelHandler } = useMixpanel()
const { networkInfo } = useActiveWeb3React()

const onSetType = (type: CancelOrderType) => {
setCancelType(type)
if (!order) return
mixpanelHandler(
isEdit ? MIXPANEL_TYPE.LO_CLICK_UPDATE_TYPE : MIXPANEL_TYPE.LO_CLICK_CANCEL_TYPE,
getPayloadTracking(order, networkInfo.name, {
[isEdit ? 'edit_type' : 'cancel_type']: type === CancelOrderType.GAS_LESS_CANCEL ? 'Gasless' : 'Hard',
}),
)
}

const gasAmountDisplay = estimateGas
? `~${formatDisplayNumber(estimateGas + '', {
Expand Down Expand Up @@ -187,11 +207,17 @@ const CancelButtons = ({
buttonGasless={
<MouseoverTooltip
placement="top"
text={supportGasLessCancel ? '' : t`This chain is not supported gasless cancel. It's coming soon.`}
text={
!chainSupportGasless
? t`This chain is not supported gasless cancel. It's coming soon.`
: !orderSupportGasless
? t`This order is not supported gasless cancel. Because it was created by our old contract`
: ''
}
>
<ButtonOutlined
{...propsGasless}
onClick={() => setCancelType(CancelOrderType.GAS_LESS_CANCEL)}
onClick={() => onSetType(CancelOrderType.GAS_LESS_CANCEL)}
$disabled={disabledGasLessCancel}
disabled={disabledGasLessCancel}
>
Expand All @@ -204,7 +230,7 @@ const CancelButtons = ({
buttonHardEdit={
<ButtonOutlined
{...propsHardCancel}
onClick={() => setCancelType(CancelOrderType.HARD_CANCEL)}
onClick={() => onSetType(CancelOrderType.HARD_CANCEL)}
color={cancelType === CancelOrderType.HARD_CANCEL ? theme.primary : undefined}
>
<GasStation size={20} />
Expand Down
8 changes: 6 additions & 2 deletions src/components/swapv2/LimitOrder/Modals/CancelOrderModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -59,8 +59,10 @@ function CancelOrderModal({
const { orders = [], ordersSoftCancel = [], supportCancelGaslessAllOrders } = useAllActiveOrders(!isCancelAll)

const isOrderSupportGaslessCancel = useIsSupportSoftCancelOrder()
const { orderSupportGasless, chainSupportGasless } = isOrderSupportGaslessCancel(order)

const supportGasLessCancel = isCancelAll ? supportCancelGaslessAllOrders : orderSupportGasless

const supportGasLessCancel = isCancelAll ? supportCancelGaslessAllOrders : isOrderSupportGaslessCancel(order)
const { onClickGaslessCancel, onClickHardCancel, expiredTime, cancelStatus, setCancelStatus } = useProcessCancelOrder(
{
isOpen,
Expand Down Expand Up @@ -182,11 +184,13 @@ function CancelOrderModal({
flowState={flowState}
/>
<CancelButtons
order={order}
cancelType={cancelType}
setCancelType={setCancelType}
estimateGas={estimateGas}
buttonInfo={{
supportGasLessCancel,
orderSupportGasless: supportGasLessCancel,
chainSupportGasless,
disabledGasLessCancel,
disabledHardCancel,
cancelGaslessText,
Expand Down
3 changes: 2 additions & 1 deletion src/components/swapv2/LimitOrder/helpers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -159,9 +159,10 @@ export const getPayloadCreateOrder = (params: CreateOrderParam) => {
}
}

export const getPayloadTracking = (order: LimitOrder, networkName: string) => {
export const getPayloadTracking = (order: LimitOrder, networkName: string, payload = {}) => {
const { makerAssetSymbol, takerAssetSymbol, makingAmount, makerAssetDecimals, id } = order
return {
...payload,
from_token: makerAssetSymbol,
to_token: takerAssetSymbol,
from_network: networkName,
Expand Down
7 changes: 6 additions & 1 deletion src/components/swapv2/LimitOrder/type.ts
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,12 @@ export type CancelOrderFunction = (data: {
isEdit?: boolean
}) => Promise<CancelOrderResponse>

export type EditOrderInfo = { cancelType?: CancelOrderType; gasFee?: string; isEdit?: boolean }
export type EditOrderInfo = {
cancelType?: CancelOrderType
gasFee?: string
isEdit?: boolean
renderCancelButtons: () => JSX.Element
}

export type CancelOrderResponse = {
orders: { operatorSignatureExpiredAt: number }[]
Expand Down
7 changes: 4 additions & 3 deletions src/components/swapv2/LimitOrder/useFetchActiveAllOrders.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,10 @@ export const useIsSupportSoftCancelOrder = () => {
const { currentData: config } = useGetLOConfigQuery(chainId)
return useCallback(
(order: LimitOrder | undefined) => {
if (!order) return false
const features = config?.features || {}
return !!features?.[order.contractAddress?.toLowerCase?.()]?.supportDoubleSignature
const orderSupportGasless = !!features?.[order?.contractAddress?.toLowerCase?.() ?? '']?.supportDoubleSignature
const chainSupportGasless = Object.values(features).some(e => e.supportDoubleSignature)
return { orderSupportGasless, chainSupportGasless }
},
[config],
)
Expand All @@ -27,7 +28,7 @@ export default function useAllActiveOrders(disabled = false) {
const isSupportSoftCancel = useIsSupportSoftCancelOrder()
return useMemo(() => {
const orders = data?.orders || []
const ordersSoftCancel = orders.filter(isSupportSoftCancel)
const ordersSoftCancel = orders.filter(e => isSupportSoftCancel(e).orderSupportGasless)
return {
orders,
ordersSoftCancel,
Expand Down
Loading
Loading