Compare commits

..
Author SHA1 Message Date
Edd bf519fbfaa fix: typo fix in token readme 2022-12-29 10:05:46 +00:00
Edd c7bc64abfb fix: typo fix in explorer readme 2022-12-29 10:05:35 +00:00
Matthew Russell 7f60485c59 chore: add readmes for token and explorer e2e 2022-12-27 17:26:32 -08:00
54 changed files with 602 additions and 1047 deletions
@@ -67,7 +67,6 @@ describe('market selector', { tags: '@smoke' }, () => {
it('mobile view', () => {
cy.viewport('iphone-xr');
cy.visit(`/trading/${marketId}`);
cy.connectVegaWallet();
cy.get('[role="dialog"]').should('not.exist');
cy.getByTestId('arrow-button').click();
cy.get('[role="dialog"]').should('be.visible');
@@ -1,12 +1,13 @@
import type { ReactNode } from 'react';
import type { FieldErrors } from 'react-hook-form';
import { useMemo } from 'react';
import { DataGrid, t, toDecimal } from '@vegaprotocol/react-helpers';
import { t, toDecimal } from '@vegaprotocol/react-helpers';
import { useVegaWallet } from '@vegaprotocol/wallet';
import * as Schema from '@vegaprotocol/types';
import type { OrderSubmissionBody } from '@vegaprotocol/wallet';
import { Tooltip } from '@vegaprotocol/ui-toolkit';
import {
MarketDataGrid,
compileGridData,
MarginWarning,
isMarketInAuction,
@@ -215,7 +216,9 @@ export const useOrderValidation = ({
<span>
{t('This market is in auction until it reaches')}{' '}
<Tooltip
description={<DataGrid grid={compileGridData(market)} />}
description={
<MarketDataGrid grid={compileGridData(market)} />
}
>
<span>{t('sufficient liquidity')}</span>
</Tooltip>
@@ -237,7 +240,9 @@ export const useOrderValidation = ({
<span>
{t('This market is in auction due to')}{' '}
<Tooltip
description={<DataGrid grid={compileGridData(market)} />}
description={
<MarketDataGrid grid={compileGridData(market)} />
}
>
<span>{t('high price volatility')}</span>
</Tooltip>
@@ -276,7 +281,9 @@ export const useOrderValidation = ({
<span>
{t('This market is in auction until it reaches')}{' '}
<Tooltip
description={<DataGrid grid={compileGridData(market)} />}
description={
<MarketDataGrid grid={compileGridData(market)} />
}
>
<span>{t('sufficient liquidity')}</span>
</Tooltip>
@@ -300,7 +307,9 @@ export const useOrderValidation = ({
<span>
{t('This market is in auction due to')}{' '}
<Tooltip
description={<DataGrid grid={compileGridData(market)} />}
description={
<MarketDataGrid grid={compileGridData(market)} />
}
>
<span>{t('high price volatility')}</span>
</Tooltip>
-1
View File
@@ -4,7 +4,6 @@ NX_TENDERMINT_URL=https://n04.d.vega.xyz/tm
NX_TENDERMINT_WEBSOCKET_URL=wss://n04.d.vega.xyz/tm/websocket
NX_VEGA_URL=https://api.n04.d.vega.xyz/graphql
NX_VEGA_ENV=DEVNET
NX_BLOCK_EXPLORER=https://be.devnet1.vega.xyz/rest
# App flags
NX_EXPLORER_ASSETS=1
-1
View File
@@ -4,7 +4,6 @@ NX_TENDERMINT_URL=https://mainnet-observer-proxy01.ops.vega.xyz/
NX_TENDERMINT_WEBSOCKET_URL=wss://mainnet-observer-proxy01.ops.vega.xyz/websocket
NX_VEGA_URL=https://api.vega.xyz/query
NX_VEGA_ENV=MAINNET
NX_BLOCK_EXPLORER=https://be.explorer.vega.xyz/rest
# App flags
NX_EXPLORER_ASSETS=1
-1
View File
@@ -4,7 +4,6 @@ NX_TENDERMINT_URL=https://tm.n00.stagnet3.vega.xyz
NX_TENDERMINT_WEBSOCKET_URL=wss://tm.n00.stagnet3.vega.xyz/websocket
NX_VEGA_URL=https://api.stagnet3.vega.xyz/graphql
NX_VEGA_ENV=STAGNET3
NX_BLOCK_EXPLORER=https://be.stagnet3.vega.xyz/rest
# App flags
NX_EXPLORER_ASSETS=1
-1
View File
@@ -4,7 +4,6 @@ NX_TENDERMINT_URL=https://tm.n07.testnet.vega.xyz/tm
NX_TENDERMINT_WEBSOCKET_URL=wss://lb.testnet.vega.xyz/tm/websocket
NX_VEGA_URL=https://api.n11.testnet.vega.xyz/graphql
NX_VEGA_ENV=TESTNET
NX_BLOCK_EXPLORER=https://be.testnet.vega.xyz/rest
# App flags
NX_EXPLORER_ASSETS=1
@@ -52,8 +52,7 @@ context('Blocks page', { tags: '@regression' }, function () {
});
});
// Skipping - see https://github.com/vegaprotocol/frontend-monorepo/issues/2494
it.skip('Previous button disabled on first block', function () {
it('Previous button disabled on first block', function () {
cy.get('[data-testid="block-input"]').type('1');
cy.get('[data-testid="go-submit"]').click();
cy.get(previousBlockBtn).find('button').should('be.disabled');
+21 -19
View File
@@ -20,18 +20,19 @@ context('Home Page', function () {
1: 'Height',
2: 'Uptime',
3: 'Total nodes',
4: 'Total staked',
5: 'Backlog',
6: 'Trades / second',
7: 'Orders / block',
8: 'Orders / second',
9: 'Transactions / block',
10: 'Block time',
11: 'Time',
12: 'App',
13: 'Tendermint',
14: 'Up since',
15: 'Chain ID',
4: 'Inactive nodes',
5: 'Total staked',
6: 'Backlog',
7: 'Trades / second',
8: 'Orders / block',
9: 'Orders / second',
10: 'Transactions / block',
11: 'Block time',
12: 'Time',
13: 'App',
14: 'Tendermint',
15: 'Up since',
16: 'Chain ID',
};
cy.get('[data-testid="stats-title"]')
@@ -39,7 +40,7 @@ context('Home Page', function () {
cy.wrap($list).should('have.text', statTitles[index]);
})
.then(($list) => {
cy.wrap($list).should('have.length', 16);
cy.wrap($list).should('have.length', 17);
});
cy.get(statsValue).eq(0).should('have.text', 'CONNECTED');
@@ -49,29 +50,30 @@ context('Home Page', function () {
.invoke('text')
.should('match', /\d+d \d+h \d+m \d+s/i);
cy.get(statsValue).eq(3).should('have.text', '2');
cy.get(statsValue).eq(4).should('have.text', '2');
cy.get(statsValue)
.eq(4)
.eq(5)
.invoke('text')
.should('match', /\d+\.\d\d(?!\d)/i);
cy.get(statsValue).eq(5).should('have.text', '0');
cy.get(statsValue).eq(6).should('have.text', '0');
cy.get(statsValue).eq(7).should('have.text', '0');
cy.get(statsValue).eq(8).should('have.text', '0');
cy.get(statsValue).eq(9).should('not.be.empty');
cy.get(statsValue).eq(9).should('have.text', '0');
cy.get(statsValue).eq(10).should('not.be.empty');
cy.get(statsValue).eq(11).should('not.be.empty');
cy.get(statsValue).eq(12).should('not.be.empty');
if (Cypress.env('NIGHTLY_RUN') != true) {
cy.get(statsValue)
.eq(12)
.eq(13)
.invoke('text')
.should('match', /v\d+\.\d+\.\d+/i);
}
cy.get(statsValue)
.eq(13)
.eq(14)
.invoke('text')
.should('match', /\d+\.\d+\.\d+/i);
cy.get(statsValue).eq(14).should('not.be.empty');
cy.get(statsValue).eq(15).should('not.be.empty');
cy.get(statsValue).eq(16).should('not.be.empty');
});
it('Block height should be updating', function () {
@@ -2,3 +2,4 @@ export { TxList } from './tx-list';
export { TxOrderType } from './tx-order-type';
export { TxsInfiniteList } from './txs-infinite-list';
export { TxsInfiniteListItem } from './txs-infinite-list-item';
export { TxsStatsInfo } from './txs-stats-info';
@@ -1,4 +1,5 @@
import { Routes } from '../../routes/route-names';
import { DATA_SOURCES } from '../../config';
import { RenderFetched } from '../render-fetched';
import { TruncatedLink } from '../truncate/truncated-link';
import { TxOrderType } from './tx-order-type';
@@ -7,7 +8,6 @@ import { t, useFetch } from '@vegaprotocol/react-helpers';
import type { BlockExplorerTransactions } from '../../routes/types/block-explorer-response';
import isNumber from 'lodash/isNumber';
import { ChainResponseCode } from './details/chain-response-code/chain-reponse.code';
import { getTxsDataUrl } from '../../hooks/use-txs-data';
interface TxsPerBlockProps {
blockHeight: string;
@@ -17,11 +17,15 @@ interface TxsPerBlockProps {
const truncateLength = 5;
export const TxsPerBlock = ({ blockHeight, txCount }: TxsPerBlockProps) => {
const filters = `filters[block.height]=${blockHeight}`;
const url = getTxsDataUrl({ limit: txCount.toString(), filters });
// TODO after https://github.com/vegaprotocol/vega/pull/6958/files is merged and deployed, use filter
// by block height instead
const {
state: { data, loading, error },
} = useFetch<BlockExplorerTransactions>(url);
} = useFetch<BlockExplorerTransactions>(
`${
DATA_SOURCES.blockExplorerUrl
}/transactions?before=${blockHeight.toString()}.0&limit=${txCount}`
);
return (
<RenderFetched error={error} loading={loading} className="text-body-large">
@@ -0,0 +1,77 @@
import { t } from '@vegaprotocol/react-helpers';
import { useEffect } from 'react';
import { InfoBlock } from '../../components/info-block';
import { Panel } from '../../components/panel';
import { useExplorerStatsQuery } from './__generated__/Explorer-stats';
import type { ExplorerStatsFieldsFragment } from './__generated__/Explorer-stats';
interface StatsMap {
field: keyof ExplorerStatsFieldsFragment;
label: string;
info: string;
}
export const TXS_STATS_MAP: StatsMap[] = [
{
field: 'averageOrdersPerBlock',
label: t('Orders per block'),
info: t(
'Number of new orders processed in the last block. All orders derived from pegged orders and liquidity commitments count as a single order'
),
},
{
field: 'txPerBlock',
label: t('Transactions per block'),
info: t('Number of transactions processed in the last block'),
},
{
field: 'tradesPerSecond',
label: t('Trades per second'),
info: t('Number of trades processed in the last second'),
},
{
field: 'ordersPerSecond',
label: t('Order per second'),
info: t(
'Number of orders processed in the last second. All orders derived from pegged orders and liquidity commitments count as a single order'
),
},
];
interface TxsStatsInfoProps {
className?: string;
}
export const TxsStatsInfo = ({ className }: TxsStatsInfoProps) => {
const { data, startPolling, stopPolling } = useExplorerStatsQuery();
useEffect(() => {
startPolling(1000);
return () => stopPolling();
});
const gridStyles =
'grid grid-rows-2 gap-4 grid-cols-2 xl:gap-8 xl:grid-rows-1 xl:grid-cols-4';
return (
<Panel className={className}>
<section className={gridStyles}>
{TXS_STATS_MAP.map((field) => {
if (!data?.statistics) {
return null;
}
// Workaround for awkward typing
const title = data.statistics[field.field] || '';
return (
<InfoBlock
subtitle={field.label}
tooltipInfo={field.info}
title={title}
/>
);
})}
</section>
</Panel>
);
};
@@ -1,7 +1,7 @@
import { t } from '@vegaprotocol/react-helpers';
import { RouteTitle } from '../../../components/route-title';
import { BlocksRefetch } from '../../../components/blocks';
import { TxsInfiniteList } from '../../../components/txs';
import { TxsInfiniteList, TxsStatsInfo } from '../../../components/txs';
import { useTxsData } from '../../../hooks/use-txs-data';
import { useDocumentTitle } from '../../../hooks/use-document-title';
@@ -16,6 +16,7 @@ export const TxsList = () => {
<section className="md:p-2 lg:p-4 xl:p-6">
<RouteTitle>{t('Transactions')}</RouteTitle>
<BlocksRefetch refetch={refreshTxs} />
<TxsStatsInfo className="!my-12 py-8" />
<TxsInfiniteList
hasMoreTxs={hasMoreTxs}
areTxsLoading={loading}
+63 -424
View File
@@ -1,70 +1,4 @@
[
{
"tranche_id": 47,
"tranche_start": "2023-12-01T00:00:00.000Z",
"tranche_end": "2023-12-01T00:00:00.000Z",
"total_added": "3000",
"total_removed": "0",
"locked_amount": "3000",
"deposits": [
{
"amount": "3000",
"user": "0xD18ffAa4a1d16f9eD9d3BE4078738Eeda3f160FD",
"tx": "0xd4db7b194e49ecf5c65e6a64f34d43b8caf51a49be0a6c2744fa4b45667969bb"
}
],
"withdrawals": [],
"users": [
{
"address": "0xD18ffAa4a1d16f9eD9d3BE4078738Eeda3f160FD",
"deposits": [
{
"amount": "3000",
"user": "0xD18ffAa4a1d16f9eD9d3BE4078738Eeda3f160FD",
"tranche_id": 47,
"tx": "0xd4db7b194e49ecf5c65e6a64f34d43b8caf51a49be0a6c2744fa4b45667969bb"
}
],
"withdrawals": [],
"total_tokens": "3000",
"withdrawn_tokens": "0",
"remaining_tokens": "3000"
}
]
},
{
"tranche_id": 48,
"tranche_start": "2022-12-01T00:00:00.000Z",
"tranche_end": "2023-06-01T00:00:00.000Z",
"total_added": "2500",
"total_removed": "0",
"locked_amount": "2053.48827966015475",
"deposits": [
{
"amount": "2500",
"user": "0xc704dA0E96a6b910fFA8d3F9f667d3D35Db8e5a1",
"tx": "0xd4db7b194e49ecf5c65e6a64f34d43b8caf51a49be0a6c2744fa4b45667969bb"
}
],
"withdrawals": [],
"users": [
{
"address": "0xc704dA0E96a6b910fFA8d3F9f667d3D35Db8e5a1",
"deposits": [
{
"amount": "2500",
"user": "0xc704dA0E96a6b910fFA8d3F9f667d3D35Db8e5a1",
"tranche_id": 48,
"tx": "0xd4db7b194e49ecf5c65e6a64f34d43b8caf51a49be0a6c2744fa4b45667969bb"
}
],
"withdrawals": [],
"total_tokens": "2500",
"withdrawn_tokens": "0",
"remaining_tokens": "2500"
}
]
},
{
"tranche_id": 45,
"tranche_start": "2023-05-01T00:00:00.000Z",
@@ -417,7 +351,7 @@
"tranche_end": "2023-12-05T00:00:00.000Z",
"total_added": "129999.45",
"total_removed": "0",
"locked_amount": "79824.868625972606079195",
"locked_amount": "81189.00181109020553229",
"deposits": [
{
"amount": "129999.45",
@@ -483,7 +417,7 @@
"tranche_end": "2023-09-03T00:00:00.000Z",
"total_added": "52600",
"total_removed": "0",
"locked_amount": "35089.81260147133078",
"locked_amount": "35918.4961123794978",
"deposits": [
{
"amount": "2600",
@@ -656,7 +590,7 @@
"tranche_end": "2023-09-17T00:00:00.000Z",
"total_added": "5000",
"total_removed": "0",
"locked_amount": "3527.314339167935",
"locked_amount": "3606.086536022324",
"deposits": [
{
"amount": "5000",
@@ -867,7 +801,7 @@
"tranche_end": "2023-04-05T00:00:00.000Z",
"total_added": "97499.58",
"total_removed": "0",
"locked_amount": "21522.9617221244380156524",
"locked_amount": "22861.0493019706346484468",
"deposits": [
{
"amount": "97499.58",
@@ -900,7 +834,7 @@
"tranche_end": "2023-04-05T00:00:00.000Z",
"total_added": "135173.4239508",
"total_removed": "98230.390980249184455396",
"locked_amount": "29418.17288981664392882194152",
"locked_amount": "31247.107600282979940660298716",
"deposits": [
{
"amount": "135173.4239508",
@@ -946,7 +880,7 @@
"tranche_end": "2023-04-05T00:00:00.000Z",
"total_added": "32499.86",
"total_removed": "0",
"locked_amount": "9054.338314829455261162",
"locked_amount": "9617.248652134231053772",
"deposits": [
{
"amount": "32499.86",
@@ -979,7 +913,7 @@
"tranche_end": "2023-04-05T00:00:00.000Z",
"total_added": "10833.29",
"total_removed": "0",
"locked_amount": "2947.0992602576930091154",
"locked_amount": "3130.321112697780704066",
"deposits": [
{
"amount": "10833.29",
@@ -1012,7 +946,7 @@
"tranche_end": "2023-04-05T00:00:00.000Z",
"total_added": "22749.93",
"total_removed": "0",
"locked_amount": "11016.9152575752619910169",
"locked_amount": "11701.839463857984444507",
"deposits": [
{
"amount": "6500",
@@ -1151,7 +1085,7 @@
"tranche_end": "2023-05-01T00:00:00.000Z",
"total_added": "22500",
"total_removed": "2310.007577475",
"locked_amount": "14729.91050874769875",
"locked_amount": "15444.7355547882135",
"deposits": [
{
"amount": "7500",
@@ -1261,7 +1195,7 @@
"tranche_end": "2023-06-02T00:00:00.000Z",
"total_added": "1939928.38",
"total_removed": "928642.9598472029154",
"locked_amount": "799856.1050314960634189408",
"locked_amount": "830418.589078051136755202",
"deposits": [
{
"amount": "1852091.69",
@@ -1612,8 +1546,8 @@
"tranche_start": "2022-08-01T00:00:00.000Z",
"tranche_end": "2023-02-01T00:00:00.000Z",
"total_added": "42500",
"total_removed": "24434.0787288",
"locked_amount": "6812.460528633250975",
"total_removed": "22452.0135114",
"locked_amount": "8140.6710761372795",
"deposits": [
{
"amount": "12500",
@@ -1627,11 +1561,6 @@
}
],
"withdrawals": [
{
"amount": "1982.0652174",
"user": "0x0B4e6fcE839B01ef43DA6F890FAC7B1Afb004600",
"tx": "0x46af57ef687e51b40874f6bbe7c462d756e58ec8194c7b2959b64c270242c0c2"
},
{
"amount": "3425.611413",
"user": "0x0B4e6fcE839B01ef43DA6F890FAC7B1Afb004600",
@@ -1675,12 +1604,6 @@
}
],
"withdrawals": [
{
"amount": "1982.0652174",
"user": "0x0B4e6fcE839B01ef43DA6F890FAC7B1Afb004600",
"tranche_id": 17,
"tx": "0x46af57ef687e51b40874f6bbe7c462d756e58ec8194c7b2959b64c270242c0c2"
},
{
"amount": "3425.611413",
"user": "0x0B4e6fcE839B01ef43DA6F890FAC7B1Afb004600",
@@ -1701,8 +1624,8 @@
}
],
"total_tokens": "30000",
"withdrawn_tokens": "24434.0787288",
"remaining_tokens": "5565.9212712"
"withdrawn_tokens": "22452.0135114",
"remaining_tokens": "7547.9864886"
}
]
},
@@ -32066,8 +31989,8 @@
"tranche_start": "2022-03-05T00:00:00.000Z",
"tranche_end": "2023-06-05T00:00:00.000Z",
"total_added": "3732368.4671",
"total_removed": "431193.2979482613764",
"locked_amount": "1253601.583317891468349156104",
"total_removed": "428705.3729302523069",
"locked_amount": "1300565.575097378439837757406",
"deposits": [
{
"amount": "1998.95815",
@@ -32246,11 +32169,6 @@
"user": "0xE6CacAE56Cca8dFdB7910b5A13578719D4E57DA0",
"tx": "0x96a49630063ce14e1e24e9878715d3c31d189d6dd107e01ebfceba8aa62971ba"
},
{
"amount": "2487.9250180090695",
"user": "0xE6CacAE56Cca8dFdB7910b5A13578719D4E57DA0",
"tx": "0x0c3a288c3e20316720b836d75c64f406519618b51e36592eee09ef9bb2cd6033"
},
{
"amount": "835.5431693861975",
"user": "0xE6CacAE56Cca8dFdB7910b5A13578719D4E57DA0",
@@ -32572,12 +32490,6 @@
"tranche_id": 1,
"tx": "0x96a49630063ce14e1e24e9878715d3c31d189d6dd107e01ebfceba8aa62971ba"
},
{
"amount": "2487.9250180090695",
"user": "0xE6CacAE56Cca8dFdB7910b5A13578719D4E57DA0",
"tranche_id": 1,
"tx": "0x0c3a288c3e20316720b836d75c64f406519618b51e36592eee09ef9bb2cd6033"
},
{
"amount": "835.5431693861975",
"user": "0xE6CacAE56Cca8dFdB7910b5A13578719D4E57DA0",
@@ -32796,8 +32708,8 @@
}
],
"total_tokens": "187637.95",
"withdrawn_tokens": "122735.595595498156",
"remaining_tokens": "64902.354404501844"
"withdrawn_tokens": "120247.6705774890865",
"remaining_tokens": "67390.2794225109135"
},
{
"address": "0x1A71e3ED1996CAbB91bB043f880CE963D601707e",
@@ -33303,8 +33215,8 @@
"tranche_start": "2022-06-05T00:00:00.000Z",
"tranche_end": "2023-12-05T00:00:00.000Z",
"total_added": "15870102.715470999700000001",
"total_removed": "519142.82799378314109952",
"locked_amount": "9744878.311171405961210772732982427710192",
"total_removed": "511218.93522350218767952",
"locked_amount": "9911409.6106449879859047601650237654190322",
"deposits": [
{
"amount": "16249.93",
@@ -33808,26 +33720,6 @@
}
],
"withdrawals": [
{
"amount": "434.254023685890375",
"user": "0x20CD77B9FC2f1fEDfb6F184E25f7127BFE991C8b",
"tx": "0xcd3061658585189b7db32710ccbd22291d875124025834e2ed9fd1fd2dc0a813"
},
{
"amount": "533.097878746431625",
"user": "0x20CD77B9FC2f1fEDfb6F184E25f7127BFE991C8b",
"tx": "0xdcddb180c5a97188736586ed09475d4354cdf6e8b0b041f26693b3371384da97"
},
{
"amount": "1573.9558",
"user": "0xF4c75FdbAe821C6B5DBB9f001bB23cBA58D1bA37",
"tx": "0x9d2918dd3feec63a8e6f8b777f5e570cd449d0e1c64921f0cd760fb05031c781"
},
{
"amount": "1253.72073256229405",
"user": "0xe3eB4CF43C072658401996b71D43eE26E573562D",
"tx": "0x8600dfffc88429840fddb3360b8b357708c7f6bcabd2bd8c804ee21ace11c416"
},
{
"amount": "1269.616788",
"user": "0xF4c75FdbAe821C6B5DBB9f001bB23cBA58D1bA37",
@@ -33898,36 +33790,6 @@
"user": "0x20CD77B9FC2f1fEDfb6F184E25f7127BFE991C8b",
"tx": "0x1e3efba0c9a6b7f9653f0fb5f9b24ae9c13ec801d00cf7f9333689f7432914c0"
},
{
"amount": "488.552248551145625",
"user": "0x20CD77B9FC2f1fEDfb6F184E25f7127BFE991C8b",
"tx": "0x2e647a56ae1d573955783dfae447261e5dbabf2f61557f2cf9a4f19cdfa9e0ed"
},
{
"amount": "1052.55764205514812",
"user": "0xe3eB4CF43C072658401996b71D43eE26E573562D",
"tx": "0xc48a7a49f743af0eb01f86880d6588e6feaca2f4799b8152785beda0cc344ce3"
},
{
"amount": "1097.830494",
"user": "0xF4c75FdbAe821C6B5DBB9f001bB23cBA58D1bA37",
"tx": "0x5d349afe6cec5ee1fb67bac724a75edf970d1004a8bd2ea8a6972a5a01319d09"
},
{
"amount": "136.685622803434",
"user": "0xE6CacAE56Cca8dFdB7910b5A13578719D4E57DA0",
"tx": "0xdbd515fed722081d9e1b03b6930f017f1df6de1cdc738a89a45716448dd708ad"
},
{
"amount": "0",
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
"tx": "0x77f7f390d59f8c85b75ad1db9dabd6dacdaf04b937f8a9e03520fdc3346857e2"
},
{
"amount": "1353.238327876609625",
"user": "0x20CD77B9FC2f1fEDfb6F184E25f7127BFE991C8b",
"tx": "0x40012432e4e417e6fb47f2c698fdb157e248ce34242bfa3a48e3755d0015a21d"
},
{
"amount": "930.302108",
"user": "0xF4c75FdbAe821C6B5DBB9f001bB23cBA58D1bA37",
@@ -35186,18 +35048,6 @@
}
],
"withdrawals": [
{
"amount": "434.254023685890375",
"user": "0x20CD77B9FC2f1fEDfb6F184E25f7127BFE991C8b",
"tranche_id": 2,
"tx": "0xcd3061658585189b7db32710ccbd22291d875124025834e2ed9fd1fd2dc0a813"
},
{
"amount": "533.097878746431625",
"user": "0x20CD77B9FC2f1fEDfb6F184E25f7127BFE991C8b",
"tranche_id": 2,
"tx": "0xdcddb180c5a97188736586ed09475d4354cdf6e8b0b041f26693b3371384da97"
},
{
"amount": "946.199315941372625",
"user": "0x20CD77B9FC2f1fEDfb6F184E25f7127BFE991C8b",
@@ -35240,18 +35090,6 @@
"tranche_id": 2,
"tx": "0x1e3efba0c9a6b7f9653f0fb5f9b24ae9c13ec801d00cf7f9333689f7432914c0"
},
{
"amount": "488.552248551145625",
"user": "0x20CD77B9FC2f1fEDfb6F184E25f7127BFE991C8b",
"tranche_id": 2,
"tx": "0x2e647a56ae1d573955783dfae447261e5dbabf2f61557f2cf9a4f19cdfa9e0ed"
},
{
"amount": "1353.238327876609625",
"user": "0x20CD77B9FC2f1fEDfb6F184E25f7127BFE991C8b",
"tranche_id": 2,
"tx": "0x40012432e4e417e6fb47f2c698fdb157e248ce34242bfa3a48e3755d0015a21d"
},
{
"amount": "2074.139541638025125",
"user": "0x20CD77B9FC2f1fEDfb6F184E25f7127BFE991C8b",
@@ -36142,8 +35980,8 @@
}
],
"total_tokens": "259998.8875",
"withdrawn_tokens": "99951.827571877045875",
"remaining_tokens": "160047.059928122954125"
"withdrawn_tokens": "97142.685093016968625",
"remaining_tokens": "162856.202406983031375"
},
{
"address": "0x89051CAb67Bc7F8CC44F7e270c6EDaf1EC57676c",
@@ -36364,12 +36202,6 @@
}
],
"withdrawals": [
{
"amount": "1253.72073256229405",
"user": "0xe3eB4CF43C072658401996b71D43eE26E573562D",
"tranche_id": 2,
"tx": "0x8600dfffc88429840fddb3360b8b357708c7f6bcabd2bd8c804ee21ace11c416"
},
{
"amount": "1168.32562674918194",
"user": "0xe3eB4CF43C072658401996b71D43eE26E573562D",
@@ -36382,12 +36214,6 @@
"tranche_id": 2,
"tx": "0x06a5b5862308d83bda5de42c3ce7f692d528d61da7d77e7698488ece926e8e53"
},
{
"amount": "1052.55764205514812",
"user": "0xe3eB4CF43C072658401996b71D43eE26E573562D",
"tranche_id": 2,
"tx": "0xc48a7a49f743af0eb01f86880d6588e6feaca2f4799b8152785beda0cc344ce3"
},
{
"amount": "1055.19046635722995",
"user": "0xe3eB4CF43C072658401996b71D43eE26E573562D",
@@ -36528,8 +36354,8 @@
}
],
"total_tokens": "150551.801",
"withdrawn_tokens": "57965.75985298627875",
"remaining_tokens": "92586.04114701372125"
"withdrawn_tokens": "55659.48147836883658",
"remaining_tokens": "94892.31952163116342"
},
{
"address": "0x4d982Ab0823fD2f48e934a7be2bb0a5374a26148",
@@ -36731,12 +36557,6 @@
}
],
"withdrawals": [
{
"amount": "1573.9558",
"user": "0xF4c75FdbAe821C6B5DBB9f001bB23cBA58D1bA37",
"tranche_id": 2,
"tx": "0x9d2918dd3feec63a8e6f8b777f5e570cd449d0e1c64921f0cd760fb05031c781"
},
{
"amount": "1269.616788",
"user": "0xF4c75FdbAe821C6B5DBB9f001bB23cBA58D1bA37",
@@ -36755,12 +36575,6 @@
"tranche_id": 2,
"tx": "0xaa6324943437bf4c7cfd5e768371d0f23b2e9e4a93e3f0be5a790607524b3a77"
},
{
"amount": "1097.830494",
"user": "0xF4c75FdbAe821C6B5DBB9f001bB23cBA58D1bA37",
"tranche_id": 2,
"tx": "0x5d349afe6cec5ee1fb67bac724a75edf970d1004a8bd2ea8a6972a5a01319d09"
},
{
"amount": "930.302108",
"user": "0xF4c75FdbAe821C6B5DBB9f001bB23cBA58D1bA37",
@@ -36865,8 +36679,8 @@
}
],
"total_tokens": "200000",
"withdrawn_tokens": "76915.699344",
"remaining_tokens": "123084.300656"
"withdrawn_tokens": "74243.91305",
"remaining_tokens": "125756.08695"
},
{
"address": "0x1b956E6c00E238194B331eddEFF72Cb5f28A8d01",
@@ -37338,12 +37152,6 @@
"tranche_id": 2,
"tx": "0xd71183e476407ae537b585fa4e77b683a565390d7e4625025ff03314b417553a"
},
{
"amount": "136.685622803434",
"user": "0xE6CacAE56Cca8dFdB7910b5A13578719D4E57DA0",
"tranche_id": 2,
"tx": "0xdbd515fed722081d9e1b03b6930f017f1df6de1cdc738a89a45716448dd708ad"
},
{
"amount": "45.922183357104",
"user": "0xE6CacAE56Cca8dFdB7910b5A13578719D4E57DA0",
@@ -37544,8 +37352,8 @@
}
],
"total_tokens": "12362.05",
"withdrawn_tokens": "4667.9832592565235",
"remaining_tokens": "7694.0667407434765"
"withdrawn_tokens": "4531.2976364530895",
"remaining_tokens": "7830.7523635469105"
},
{
"address": "0xb091D456d0dFCB94dcba6f355379056C5bb995fC",
@@ -38176,8 +37984,8 @@
"tranche_start": "2021-11-05T00:00:00.000Z",
"tranche_end": "2023-05-05T00:00:00.000Z",
"total_added": "14597706.0446472999",
"total_removed": "3524412.62195988798093986",
"locked_amount": "3274964.208947641866344369334082668",
"total_removed": "3489401.90950082536320653",
"locked_amount": "3428704.84130926731572974432005816",
"deposits": [
{
"amount": "129284.449",
@@ -38386,31 +38194,6 @@
}
],
"withdrawals": [
{
"amount": "12758.73908063512839093",
"user": "0x91715128a71c9C734CDC20E5EdEEeA02E72e428E",
"tx": "0x41db06e3a05adf4be2d61eab5929825225a23051f0aaa5aca1ddd5760e188fa4"
},
{
"amount": "3671.528996246291985",
"user": "0xcc2cf726A84e71301f9079FC177BA946aa98A694",
"tx": "0xbdb207cce4094c7372c7a99f7e851c5d781883d24898fa285ae19eda27b50840"
},
{
"amount": "14686.9255071873432384",
"user": "0x47FbE34Fd93416c63d35544dEE6c6f442Db8513d",
"tx": "0xeda94e6e1582e8045c91d54b11d240bb9e1f49467bd16ae4e89727b5de9b9a82"
},
{
"amount": "762.7902369187144135",
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
"tx": "0x1fd0d4536451cf9f0b80832a66c6d8f4ca2a05f1c96f84f4679c94fd319fb4cb"
},
{
"amount": "738.21651322227936725",
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
"tx": "0x5edbba4195383ca3e47fe551b0579ddba8ce13cc93d455f8d678f6c315a5b297"
},
{
"amount": "1289.16117292541627425",
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
@@ -38456,16 +38239,6 @@
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
"tx": "0x617ff95943d9685aaf9763e3fb4ca1f81e8dd04fd013d1a64b59e52b78b25b81"
},
{
"amount": "678.47222286845557075",
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
"tx": "0x40dc4dbfbf26c199c7cf1be4b281d553d470a830423ff678795585588d1c5cd0"
},
{
"amount": "1714.0399019844047675",
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
"tx": "0x4139309b9927ce8486e61491dd9ba7a31f36cc112dd6446c3d33ad897f14264c"
},
{
"amount": "9158.56255453299474378",
"user": "0x66827bCD635f2bB1779d68c46aEB16541bCA6ba8",
@@ -41032,18 +40805,6 @@
}
],
"withdrawals": [
{
"amount": "762.7902369187144135",
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
"tranche_id": 3,
"tx": "0x1fd0d4536451cf9f0b80832a66c6d8f4ca2a05f1c96f84f4679c94fd319fb4cb"
},
{
"amount": "738.21651322227936725",
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
"tranche_id": 3,
"tx": "0x5edbba4195383ca3e47fe551b0579ddba8ce13cc93d455f8d678f6c315a5b297"
},
{
"amount": "1289.16117292541627425",
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
@@ -41092,18 +40853,6 @@
"tranche_id": 3,
"tx": "0x617ff95943d9685aaf9763e3fb4ca1f81e8dd04fd013d1a64b59e52b78b25b81"
},
{
"amount": "678.47222286845557075",
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
"tranche_id": 3,
"tx": "0x40dc4dbfbf26c199c7cf1be4b281d553d470a830423ff678795585588d1c5cd0"
},
{
"amount": "1714.0399019844047675",
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
"tranche_id": 3,
"tx": "0x4139309b9927ce8486e61491dd9ba7a31f36cc112dd6446c3d33ad897f14264c"
},
{
"amount": "2874.6686339993457875",
"user": "0x4Aa3c35F6CC2d507E5C18205ee57099A4C80B19b",
@@ -43284,8 +43033,8 @@
}
],
"total_tokens": "359123.469575",
"withdrawn_tokens": "278002.50185993092563925",
"remaining_tokens": "81120.96771506907436075"
"withdrawn_tokens": "274108.98298493707152025",
"remaining_tokens": "85014.48659006292847975"
},
{
"address": "0xBdd412797c1B78535Afc5F71503b91fAbD0160fB",
@@ -43444,12 +43193,6 @@
}
],
"withdrawals": [
{
"amount": "3671.528996246291985",
"user": "0xcc2cf726A84e71301f9079FC177BA946aa98A694",
"tranche_id": 3,
"tx": "0xbdb207cce4094c7372c7a99f7e851c5d781883d24898fa285ae19eda27b50840"
},
{
"amount": "7412.8453939926209526",
"user": "0xcc2cf726A84e71301f9079FC177BA946aa98A694",
@@ -43494,8 +43237,8 @@
}
],
"total_tokens": "66299.71746",
"withdrawn_tokens": "51123.4692205231870044",
"remaining_tokens": "15176.2482394768129956"
"withdrawn_tokens": "47451.9402242768950194",
"remaining_tokens": "18847.7772357231049806"
},
{
"address": "0x66827bCD635f2bB1779d68c46aEB16541bCA6ba8",
@@ -43896,12 +43639,6 @@
}
],
"withdrawals": [
{
"amount": "14686.9255071873432384",
"user": "0x47FbE34Fd93416c63d35544dEE6c6f442Db8513d",
"tranche_id": 3,
"tx": "0xeda94e6e1582e8045c91d54b11d240bb9e1f49467bd16ae4e89727b5de9b9a82"
},
{
"amount": "29651.7863357455771104",
"user": "0x47FbE34Fd93416c63d35544dEE6c6f442Db8513d",
@@ -43946,8 +43683,8 @@
}
],
"total_tokens": "265198.86984",
"withdrawn_tokens": "204494.416564444861116",
"remaining_tokens": "60704.453275555138884"
"withdrawn_tokens": "189807.4910572575178776",
"remaining_tokens": "75391.3787827424821224"
},
{
"address": "0x35022e6c85B50F4904C7BC7e692A9F3bbEE8D2CE",
@@ -44124,12 +43861,6 @@
}
],
"withdrawals": [
{
"amount": "12758.73908063512839093",
"user": "0x91715128a71c9C734CDC20E5EdEEeA02E72e428E",
"tranche_id": 3,
"tx": "0x41db06e3a05adf4be2d61eab5929825225a23051f0aaa5aca1ddd5760e188fa4"
},
{
"amount": "25760.51683291284616209",
"user": "0x91715128a71c9C734CDC20E5EdEEeA02E72e428E",
@@ -44168,8 +43899,8 @@
}
],
"total_tokens": "230391.5181735",
"withdrawn_tokens": "177653.41087820324320647",
"remaining_tokens": "52738.10729529675679353"
"withdrawn_tokens": "164894.67179756811481554",
"remaining_tokens": "65496.84637593188518446"
},
{
"address": "0xC6b2864fbCD2A8dEC8DEfD1D421bC1E450C370AD",
@@ -44546,8 +44277,8 @@
"tranche_start": "2021-10-05T00:00:00.000Z",
"tranche_end": "2023-04-05T00:00:00.000Z",
"total_added": "5778205.3912159303",
"total_removed": "2488390.855746378035859668",
"locked_amount": "977054.762233663485683568233933439",
"total_removed": "2479228.813551817124120168",
"locked_amount": "1037798.493633229255945123020263576",
"deposits": [
{
"amount": "552496.6455",
@@ -44691,11 +44422,6 @@
}
],
"withdrawals": [
{
"amount": "9162.0421945609117395",
"user": "0x91715128a71c9C734CDC20E5EdEEeA02E72e428E",
"tx": "0xb3ccc6e824ffee15c67e8a0779dac9758deec01360025608c616a78f2670ad15"
},
{
"amount": "4206.439644984274503",
"user": "0xafa64cCa337eFEE0AD827F6C2684e69275226e90",
@@ -45380,12 +45106,6 @@
}
],
"withdrawals": [
{
"amount": "9162.0421945609117395",
"user": "0x91715128a71c9C734CDC20E5EdEEeA02E72e428E",
"tranche_id": 4,
"tx": "0xb3ccc6e824ffee15c67e8a0779dac9758deec01360025608c616a78f2670ad15"
},
{
"amount": "18498.907302984077175",
"user": "0x91715128a71c9C734CDC20E5EdEEeA02E72e428E",
@@ -45424,8 +45144,8 @@
}
],
"total_tokens": "165749.29365",
"withdrawn_tokens": "136968.1104261044661675",
"remaining_tokens": "28781.1832238955338325"
"withdrawn_tokens": "127806.068231543554428",
"remaining_tokens": "37943.225418456445572"
},
{
"address": "0x72e7BB93E73b2885a22CA29c34759361399a5C0e",
@@ -46353,8 +46073,8 @@
"tranche_start": "2022-06-05T00:00:00.000Z",
"tranche_end": "2023-06-05T00:00:00.000Z",
"total_added": "472355.6199999996",
"total_removed": "27768.7412941819005",
"locked_amount": "198640.336768870982365068290208",
"total_removed": "27238.3679206278963",
"locked_amount": "206082.034745654336161635141856908",
"deposits": [
{
"amount": "3000",
@@ -52973,16 +52693,6 @@
}
],
"withdrawals": [
{
"amount": "229.648541348",
"user": "0x65C13724928ea0AfA68e09c7b70449bB8f6f3Fc8",
"tx": "0x9e93ae11a21aaa47b37494eb70d38c3b56117d894244398f33ba495006e785fd"
},
{
"amount": "115.710343734",
"user": "0x57d7881125E8057B0e8D90B7A2Cc8dACC72F8659",
"tx": "0x9b16067ba1c2dfbb487fb60690c377cd8a500211c2d6d354daadab71d706b381"
},
{
"amount": "20.707914768",
"user": "0x4eD2b3c68BB4fda084ce1591a210F4aC8b71234A",
@@ -53038,21 +52748,6 @@
"user": "0xeE2C02Cd75dcEacD16614feB126a1cD2637646d0",
"tx": "0x81181699f4cae02ba8761ccf126f88141644a318f8f5bfd67f3d4a4f870b59e9"
},
{
"amount": "97.792503807",
"user": "0xdc040917f80aC350460e55467e4B6c52Fc5e220E",
"tx": "0x1f8e5bff5b6390c9de0c33a77494fda9ce1876e11e39400d9fe1d7ef4da9e679"
},
{
"amount": "58.7576011050042",
"user": "0x91Ff7FADb80385D2E25E12F92d211688a550A06C",
"tx": "0x87ae337c9809d80018c3f2c3b90df597bea0b3ac865fb58f8471ff92ebcbadd8"
},
{
"amount": "28.46438356",
"user": "0x7C8D2D8BcFffcD48dBcb65C5Bb7588B66dcD22bb",
"tx": "0x8148604cfba3cabb5229c19cd857c8c47255c1502bddc9871c01b05cf569c691"
},
{
"amount": "199.140778792",
"user": "0x2827B97046558f044ab07c3De0159632f8956472",
@@ -66566,12 +66261,6 @@
}
],
"withdrawals": [
{
"amount": "28.46438356",
"user": "0x7C8D2D8BcFffcD48dBcb65C5Bb7588B66dcD22bb",
"tranche_id": 5,
"tx": "0x8148604cfba3cabb5229c19cd857c8c47255c1502bddc9871c01b05cf569c691"
},
{
"amount": "35.005327244",
"user": "0x7C8D2D8BcFffcD48dBcb65C5Bb7588B66dcD22bb",
@@ -66592,8 +66281,8 @@
}
],
"total_tokens": "400",
"withdrawn_tokens": "228.378069504",
"remaining_tokens": "171.621930496"
"withdrawn_tokens": "199.913685944",
"remaining_tokens": "200.086314056"
},
{
"address": "0xc56F9f1d5f124655FA9CB8f85C7701E13a2fBF4D",
@@ -71885,17 +71574,10 @@
"tx": "0xc8541da6a57f410b6faba47a5e5184bae700193b7bd042914fffc562114d92f5"
}
],
"withdrawals": [
{
"amount": "58.7576011050042",
"user": "0x91Ff7FADb80385D2E25E12F92d211688a550A06C",
"tranche_id": 5,
"tx": "0x87ae337c9809d80018c3f2c3b90df597bea0b3ac865fb58f8471ff92ebcbadd8"
}
],
"withdrawals": [],
"total_tokens": "103.38",
"withdrawn_tokens": "58.7576011050042",
"remaining_tokens": "44.6223988949958"
"withdrawn_tokens": "0",
"remaining_tokens": "103.38"
},
{
"address": "0x942e32E60f465f5DCDc071840E9D9D6a3D619dE7",
@@ -72025,17 +71707,10 @@
"tx": "0xc8541da6a57f410b6faba47a5e5184bae700193b7bd042914fffc562114d92f5"
}
],
"withdrawals": [
{
"amount": "229.648541348",
"user": "0x65C13724928ea0AfA68e09c7b70449bB8f6f3Fc8",
"tranche_id": 5,
"tx": "0x9e93ae11a21aaa47b37494eb70d38c3b56117d894244398f33ba495006e785fd"
}
],
"withdrawals": [],
"total_tokens": "400",
"withdrawn_tokens": "229.648541348",
"remaining_tokens": "170.351458652"
"withdrawn_tokens": "0",
"remaining_tokens": "400"
},
{
"address": "0x4FF4255c498e844cE78F9F9aD46913A20A1642b4",
@@ -72990,12 +72665,6 @@
}
],
"withdrawals": [
{
"amount": "97.792503807",
"user": "0xdc040917f80aC350460e55467e4B6c52Fc5e220E",
"tranche_id": 5,
"tx": "0x1f8e5bff5b6390c9de0c33a77494fda9ce1876e11e39400d9fe1d7ef4da9e679"
},
{
"amount": "29.694815448",
"user": "0xdc040917f80aC350460e55467e4B6c52Fc5e220E",
@@ -73010,8 +72679,8 @@
}
],
"total_tokens": "300",
"withdrawn_tokens": "170.4241914",
"remaining_tokens": "129.5758086"
"withdrawn_tokens": "72.631687593",
"remaining_tokens": "227.368312407"
},
{
"address": "0x8D01053B4f4857Ff453CAeDBf8387Cd57a5a2A2b",
@@ -73988,17 +73657,10 @@
"tx": "0xe32a466fc780a0fb3fd84a804f622931ebfaf3f428bff0dc6d141270410e75f8"
}
],
"withdrawals": [
{
"amount": "115.710343734",
"user": "0x57d7881125E8057B0e8D90B7A2Cc8dACC72F8659",
"tranche_id": 5,
"tx": "0x9b16067ba1c2dfbb487fb60690c377cd8a500211c2d6d354daadab71d706b381"
}
],
"withdrawals": [],
"total_tokens": "200",
"withdrawn_tokens": "115.710343734",
"remaining_tokens": "84.289656266"
"withdrawn_tokens": "0",
"remaining_tokens": "200"
},
{
"address": "0x89F3Db3ce23E58A3C416D5930d7E806d80E4F1FF",
@@ -74455,7 +74117,7 @@
"tranche_start": "2021-12-05T00:00:00.000Z",
"tranche_end": "2022-06-05T00:00:00.000Z",
"total_added": "171288.42",
"total_removed": "60849.0699829322989",
"total_removed": "60641.2093106172989",
"locked_amount": "0",
"deposits": [
{
@@ -78710,16 +78372,6 @@
"user": "0x667B436A05523B8D80483b030f559f034753DD74",
"tx": "0x48d6761a237f75fa95ff67082e4f0b5538586a58a7a677943f1c4260f3abb860"
},
{
"amount": "150",
"user": "0x300E9b1628eE5949365B7f6c08690C2B9ae2043A",
"tx": "0x3873e5c2e039043676e6e705feedd49a367c85d9e69aef64d695472bce689908"
},
{
"amount": "57.860672315",
"user": "0x0Fa5387417ce5030a259b48f1bde2001a100D27B",
"tx": "0x41b8c1181cf49b5d873bf94d03d3932b38705d6cbb5bc147026910ffcc480c0b"
},
{
"amount": "250",
"user": "0x3E1CECDc3d15Cb03e91a60470C4453f4fBFc75F9",
@@ -81433,12 +81085,6 @@
}
],
"withdrawals": [
{
"amount": "57.860672315",
"user": "0x0Fa5387417ce5030a259b48f1bde2001a100D27B",
"tranche_id": 6,
"tx": "0x41b8c1181cf49b5d873bf94d03d3932b38705d6cbb5bc147026910ffcc480c0b"
},
{
"amount": "192.139327685",
"user": "0x0Fa5387417ce5030a259b48f1bde2001a100D27B",
@@ -81447,8 +81093,8 @@
}
],
"total_tokens": "250",
"withdrawn_tokens": "250",
"remaining_tokens": "0"
"withdrawn_tokens": "192.139327685",
"remaining_tokens": "57.860672315"
},
{
"address": "0x643E4ea2718eFA5897F5eB655D767E4193695987",
@@ -90280,17 +89926,10 @@
"tx": "0x716a7be06da5a7a3d8038907974887a31805ea8eeab5d130cba528e4d2094d9f"
}
],
"withdrawals": [
{
"amount": "150",
"user": "0x300E9b1628eE5949365B7f6c08690C2B9ae2043A",
"tranche_id": 6,
"tx": "0x3873e5c2e039043676e6e705feedd49a367c85d9e69aef64d695472bce689908"
}
],
"withdrawals": [],
"total_tokens": "150",
"withdrawn_tokens": "150",
"remaining_tokens": "0"
"withdrawn_tokens": "0",
"remaining_tokens": "150"
},
{
"address": "0x2074924ebfD97Ff2351659CB00e259eBd6451aA5",
@@ -133,7 +133,6 @@ describe('Navbar', { tags: '@smoke' }, () => {
cy.mockTradingPage();
cy.mockSubscription();
cy.visit('/');
cy.wait('@Market');
cy.getByTestId('dialog-close').click();
});
@@ -224,34 +224,4 @@ describe('home', { tags: '@regression' }, () => {
.should('exist');
});
});
describe('redirect should take last visited market into consideration', () => {
beforeEach(() => {
cy.window().then((window) => {
window.localStorage.removeItem('marketId');
});
});
it('marketId comes from existing market', () => {
cy.window().then((window) => {
window.localStorage.setItem('marketId', 'market-1');
cy.visit('/');
cy.wait('@Market');
cy.location('hash').should('equal', '#/markets/market-1');
cy.get('[role="dialog"]').should('not.exist');
});
});
it('marketId comes from not-existing market', () => {
cy.window().then((window) => {
window.localStorage.setItem('marketId', 'market-not-existing');
cy.mockGQL((req) => {
aliasGQLQuery(req, 'Market', null);
});
cy.visit('/');
cy.wait('@Market');
cy.location('hash').should('equal', '#/markets/market-not-existing');
cy.get('[role="dialog"]').should('not.exist');
});
});
});
});
@@ -30,20 +30,11 @@ const displayTomorrow = () => {
describe('time in force default values', () => {
before(() => {
cy.window().then((win) => {
win.localStorage.setItem(
'vega_wallet_config',
JSON.stringify({
token: Cypress.env('VEGA_WALLET_API_TOKEN'),
connector: 'jsonRpc',
url: 'http://localhost:1789',
})
);
});
cy.mockTradingPage();
cy.mockSubscription();
cy.visit('/#/markets/market-0');
cy.wait('@Market');
cy.connectVegaWallet();
});
it('must have market order set up to IOC by default', function () {
@@ -68,15 +59,20 @@ describe('time in force default values', () => {
describe('must submit order', { tags: '@smoke' }, () => {
// 7002-SORD-039
before(() => {
setVegaConfig();
cy.mockTradingPage();
cy.mockSubscription();
cy.visit('/#/markets/market-0');
cy.wait('@Market');
cy.connectVegaWallet();
cy.window().then(function (window) {
cy.wrap(window.localStorage.getItem('vega_wallet_config')).as('cfg');
});
});
beforeEach(() => {
setVegaConfig();
cy.window().then(function (window) {
window.localStorage.setItem('vega_wallet_config', this.cfg);
});
});
it('successfully places market buy order', () => {
@@ -162,7 +158,6 @@ describe(
{ tags: '@regression' },
() => {
before(() => {
setVegaConfig();
cy.mockTradingPage(
Schema.MarketState.STATE_SUSPENDED,
Schema.MarketTradingMode.TRADING_MODE_BATCH_AUCTION,
@@ -171,10 +166,16 @@ describe(
cy.mockSubscription();
cy.visit('/#/markets/market-0');
cy.wait('@Market');
cy.connectVegaWallet();
cy.window().then(function (window) {
cy.wrap(window.localStorage.getItem('vega_wallet_config')).as('cfg');
});
});
beforeEach(() => {
setVegaConfig();
cy.window().then(function (window) {
window.localStorage.setItem('vega_wallet_config', this.cfg);
});
});
it('successfully places limit buy order', () => {
@@ -231,7 +232,6 @@ describe(
{ tags: '@regression' },
() => {
before(() => {
setVegaConfig();
cy.mockTradingPage(
Schema.MarketState.STATE_SUSPENDED,
Schema.MarketTradingMode.TRADING_MODE_OPENING_AUCTION,
@@ -240,10 +240,16 @@ describe(
cy.mockSubscription();
cy.visit('/#/markets/market-0');
cy.wait('@Market');
cy.connectVegaWallet();
cy.window().then(function (window) {
cy.wrap(window.localStorage.getItem('vega_wallet_config')).as('cfg');
});
});
beforeEach(() => {
setVegaConfig();
cy.window().then(function (window) {
window.localStorage.setItem('vega_wallet_config', this.cfg);
});
});
it('successfully places limit buy order', () => {
@@ -300,7 +306,6 @@ describe(
{ tags: '@regression' },
() => {
before(() => {
setVegaConfig();
cy.mockTradingPage(
Schema.MarketState.STATE_SUSPENDED,
Schema.MarketTradingMode.TRADING_MODE_MONITORING_AUCTION,
@@ -309,10 +314,16 @@ describe(
cy.mockSubscription();
cy.visit('/#/markets/market-0');
cy.wait('@Market');
cy.connectVegaWallet();
cy.window().then(function (window) {
cy.wrap(window.localStorage.getItem('vega_wallet_config')).as('cfg');
});
});
beforeEach(() => {
setVegaConfig();
cy.window().then(function (window) {
window.localStorage.setItem('vega_wallet_config', this.cfg);
});
});
it('successfully places limit buy order', () => {
@@ -410,10 +421,10 @@ describe('deal ticket validation', { tags: '@smoke' }, () => {
describe('deal ticket size validation', { tags: '@smoke' }, function () {
beforeEach(() => {
setVegaConfig();
cy.mockTradingPage();
cy.visit('/#/markets/market-0');
cy.wait('@Market');
cy.connectVegaWallet();
});
it('must warn if order size input has too many digits after the decimal place', function () {
@@ -444,18 +455,14 @@ describe('deal ticket size validation', { tags: '@smoke' }, function () {
describe('limit order validations', { tags: '@smoke' }, () => {
before(() => {
setVegaConfig();
cy.mockTradingPage();
cy.mockSubscription();
cy.visit('/#/markets/market-0');
cy.connectVegaWallet();
cy.wait('@Market');
cy.getByTestId(toggleLimit).click();
});
beforeEach(() => {
setVegaConfig();
});
it('must see the price unit', function () {
//7002-SORD-018
cy.getByTestId(orderPriceField)
@@ -537,17 +544,11 @@ describe('limit order validations', { tags: '@smoke' }, () => {
describe('market order validations', { tags: '@smoke' }, () => {
before(() => {
setVegaConfig();
cy.mockTradingPage();
cy.visit('/#/markets/market-0');
cy.wait('@Market');
cy.getByTestId(toggleMarket).click();
});
beforeEach(() => {
setVegaConfig();
});
it('must not see the price unit', function () {
//7002-SORD-019
cy.getByTestId(orderPriceField).should('not.exist');
@@ -586,7 +587,6 @@ describe('market order validations', { tags: '@smoke' }, () => {
describe('suspended market validation', { tags: '@regression' }, () => {
before(() => {
setVegaConfig();
cy.mockTradingPage(
Schema.MarketState.STATE_SUSPENDED,
Schema.MarketTradingMode.TRADING_MODE_MONITORING_AUCTION,
@@ -595,10 +595,7 @@ describe('suspended market validation', { tags: '@regression' }, () => {
cy.mockSubscription();
cy.visit('/#/markets/market-0');
cy.wait('@Market');
});
beforeEach(() => {
setVegaConfig();
cy.connectVegaWallet();
});
it('should show warning for market order', function () {
@@ -611,7 +608,6 @@ describe('suspended market validation', { tags: '@regression' }, () => {
'This market is in auction until it reaches sufficient liquidity. Only limit orders are permitted when market is in auction'
);
});
it('should show info for allowed TIF', function () {
cy.getByTestId(toggleLimit).click();
cy.getByTestId(orderPriceField).clear().type('0.1');
@@ -639,7 +635,6 @@ describe('suspended market validation', { tags: '@regression' }, () => {
describe('account validation', { tags: '@regression' }, () => {
describe('zero balance error', () => {
beforeEach(() => {
setVegaConfig();
cy.mockTradingPage();
cy.mockGQL((req) => {
aliasGQLQuery(
@@ -668,6 +663,7 @@ describe('account validation', { tags: '@regression' }, () => {
});
cy.mockSubscription();
cy.visit('/#/markets/market-0');
cy.connectVegaWallet();
cy.wait('@Market');
});
@@ -686,7 +682,6 @@ describe('account validation', { tags: '@regression' }, () => {
describe('not enough balance warning', () => {
beforeEach(() => {
setVegaConfig();
cy.mockTradingPage();
cy.mockGQL((req) => {
aliasGQLQuery(
@@ -704,9 +699,9 @@ describe('account validation', { tags: '@regression' }, () => {
});
cy.mockSubscription();
cy.visit('/#/markets/market-0');
cy.connectVegaWallet();
cy.wait('@Market');
});
it('should display info and button for deposit', () => {
//7002-SORD-003
// warning should show immediately
@@ -745,16 +740,3 @@ const createOrder = (order: OrderSubmission): void => {
}
cy.getByTestId(placeOrderBtn).click();
};
const setVegaConfig = () => {
cy.window().then((win) => {
win.localStorage.setItem(
'vega_wallet_config',
JSON.stringify({
token: Cypress.env('VEGA_WALLET_API_TOKEN'),
connector: 'jsonRpc',
url: 'http://localhost:1789',
})
);
});
};
@@ -423,9 +423,4 @@ describe('amend and cancel order', { tags: '@smoke' }, () => {
testOrderCancellation(order);
});
});
it.skip('tbd for 7003-MORD', () => {
// NOT COVERED: must see the reference, offset and direction for each part pegged order - waiting for clarification
// NOT COVERED: must see the reference, offset and direction for each part liquidity order order - waiting for clarification
// NOT COVERED: must be warned (pre-submit) if the input price has too many digits after the decimal place for the market - issues/2486
});
});
@@ -0,0 +1,11 @@
import { ethers } from 'ethers';
import type { Transaction } from '@vegaprotocol/wallet';
/**
* Base64 encode a transaction object
*/
export const encodeTransaction = (tx: Transaction): string => {
return ethers.utils.base64.encode(
ethers.utils.toUtf8Bytes(JSON.stringify(tx))
);
};
@@ -7,6 +7,7 @@ import type {
OrderSubmissionBody,
Transaction,
} from '@vegaprotocol/wallet';
import { encodeTransaction } from './encode-transaction';
export const testOrderSubmission = (
order: OrderSubmission,
@@ -17,6 +18,9 @@ export const testOrderSubmission = (
...expected,
};
expectedOrder.expiresAt = expectedOrder.expiresAt || undefined;
expectedOrder.price = expectedOrder.price || undefined;
const transaction: OrderSubmissionBody = {
orderSubmission: expectedOrder,
};
@@ -32,6 +36,9 @@ export const testOrderAmendment = (
...expected,
};
expectedOrder.expiresAt = expectedOrder.expiresAt || undefined;
expectedOrder.price = expectedOrder.price || undefined;
const transaction: OrderAmendmentBody = {
orderAmendment: expectedOrder,
};
@@ -63,7 +70,7 @@ const vegaWalletTransaction = (transaction: Transaction) => {
?.token,
publicKey: Cypress.env('VEGA_PUBLIC_KEY2'),
sendingMode: 'TYPE_SYNC',
transaction,
encodedTransaction: encodeTransaction(transaction),
});
cy.getByTestId(dialogTitle).should(
'have.text',
+34 -16
View File
@@ -1,10 +1,14 @@
import { useEffect } from 'react';
import { useNavigate } from 'react-router-dom';
import { marketsWithDataProvider } from '@vegaprotocol/market-list';
import { useDataProvider } from '@vegaprotocol/react-helpers';
import {
addDecimalsFormatNumber,
titlefy,
useDataProvider,
} from '@vegaprotocol/react-helpers';
import { AsyncRenderer } from '@vegaprotocol/ui-toolkit';
import { Links, Routes } from '../../pages/client-router';
import { useGlobalStore } from '../../stores';
import { useEffect } from 'react';
import { useNavigate } from 'react-router-dom';
import { useGlobalStore, usePageTitleStore } from '../../stores';
export const Home = () => {
const navigate = useNavigate();
@@ -13,26 +17,40 @@ export const Home = () => {
const { data, error, loading } = useDataProvider({
dataProvider: marketsWithDataProvider,
});
const update = useGlobalStore((store) => store.update);
const marketId = useGlobalStore((store) => store.marketId);
const { update } = useGlobalStore((store) => ({
update: store.update,
}));
const { pageTitle, updateTitle } = usePageTitleStore((store) => ({
pageTitle: store.pageTitle,
updateTitle: store.updateTitle,
}));
useEffect(() => {
if (marketId) {
navigate(Links[Routes.MARKET](marketId), {
replace: true,
});
} else if (data) {
const marketDataId = data[0]?.id;
if (marketDataId) {
navigate(Links[Routes.MARKET](marketDataId), {
if (data) {
const marketId = data[0]?.id;
const marketName = data[0]?.tradableInstrument.instrument.name;
const marketPrice = data[0]?.data?.markPrice
? addDecimalsFormatNumber(
data[0]?.data?.markPrice,
data[0]?.decimalPlaces
)
: null;
const newPageTitle = titlefy([marketName, marketPrice]);
if (marketId) {
navigate(Links[Routes.MARKET](marketId), {
replace: true,
});
update({ marketId });
if (pageTitle !== newPageTitle) {
updateTitle(newPageTitle);
}
} else {
navigate(Links[Routes.MARKET]());
}
update({ shouldDisplayWelcomeDialog: true });
}
}, [marketId, data, navigate, update]);
}, [data, navigate, update, pageTitle, updateTitle]);
return (
<AsyncRenderer data={data} loading={loading} error={error}>
+22 -21
View File
@@ -32,23 +32,29 @@ export interface SingleMarketData extends SingleMarketFieldsFragment {
}
export const Market = () => {
const { marketId } = useParams();
const params = useParams();
const navigate = useNavigate();
const { w } = useWindowSize();
const update = useGlobalStore((store) => store.update);
const lastMarketId = useGlobalStore((store) => store.marketId);
const marketId = params.marketId;
const pageTitle = usePageTitleStore((store) => store.pageTitle);
const updateTitle = usePageTitleStore((store) => store.updateTitle);
const { w } = useWindowSize();
const { update } = useGlobalStore((store) => ({
update: store.update,
}));
const { pageTitle, updateTitle } = usePageTitleStore((store) => ({
pageTitle: store.pageTitle,
updateTitle: store.updateTitle,
}));
const onSelect = useCallback(
(id: string) => {
if (id && id !== marketId) {
update({ marketId: id });
navigate(Links[Routes.MARKET](id));
}
},
[marketId, navigate]
[marketId, update, navigate]
);
const variables = useMemo(
@@ -58,22 +64,12 @@ export const Market = () => {
[marketId]
);
const updateMarketId = useCallback(
({ data }: { data: { id?: string } | null }) => {
if (data?.id && data.id !== lastMarketId) {
update({ marketId: data.id });
}
return true;
},
[update, lastMarketId]
);
const { data, error, loading } = useDataProvider<
SingleMarketFieldsFragment,
never
>({
dataProvider: marketProvider,
variables,
update: updateMarketId,
skip: !marketId,
});
@@ -108,10 +104,11 @@ export const Market = () => {
}
return <TradePanels market={data} onSelect={onSelect} />;
}, [w, data, onSelect]);
if (!data && marketId) {
return (
<Splash>
<p>{t('Market not found')}</p>
<p>{t('Not found')}</p>
</Splash>
);
}
@@ -122,9 +119,13 @@ export const Market = () => {
error={error}
data={data || undefined}
noDataCondition={(data) => false}
>
{tradeView}
</AsyncRenderer>
render={(data) => {
if (!data && marketId) {
return <Splash>{t('Market not found')}</Splash>;
}
return <>{tradeView}</>;
}}
/>
);
};
@@ -17,7 +17,6 @@ import { Last24hPriceChange } from '../../components/last-24h-price-change';
import { Last24hVolume } from '../../components/last-24h-volume';
import { MarketState } from '../../components/market-state';
import { MarketTradingMode } from '../../components/market-trading-mode';
import { MarketLiquiditySupplied } from '../../components/liquidity-supplied';
interface TradeMarketHeaderProps {
market: SingleMarketFieldsFragment | null;
@@ -97,10 +96,6 @@ export const TradeMarketHeader = ({
</HeaderStat>
) : null}
<MarketProposalNotification marketId={market?.id} />
<MarketLiquiditySupplied
marketId={market?.id}
assetDecimals={asset?.decimals || 0}
/>
</Header>
);
};
@@ -1,15 +1,18 @@
import { useCallback } from 'react';
import { MarketsContainer } from '@vegaprotocol/market-list';
import { useGlobalStore } from '../../stores';
import { useNavigate } from 'react-router-dom';
import { Links, Routes } from '../../pages/client-router';
export const Markets = () => {
const navigate = useNavigate();
const { update } = useGlobalStore((store) => ({ update: store.update }));
const handleOnSelect = useCallback(
(marketId: string) => {
update({ marketId });
navigate(Links[Routes.MARKET](marketId));
},
[navigate]
[update, navigate]
);
return <MarketsContainer onSelect={handleOnSelect} />;
@@ -1 +0,0 @@
export * from './liquidity-supplied';
@@ -1,130 +0,0 @@
import { useCallback, useMemo, useState } from 'react';
import {
addDecimalsFormatNumber,
formatNumberPercentage,
NetworkParams,
t,
useDataProvider,
useNetworkParams,
} from '@vegaprotocol/react-helpers';
import type {
MarketData,
MarketDataUpdateFieldsFragment,
SingleMarketFieldsFragment,
} from '@vegaprotocol/market-list';
import { marketDataProvider, marketProvider } from '@vegaprotocol/market-list';
import { HeaderStat } from '../header';
import { Link } from '@vegaprotocol/ui-toolkit';
import BigNumber from 'bignumber.js';
import { useCheckLiquidityStatus } from '@vegaprotocol/liquidity';
import { DataGrid } from '@vegaprotocol/react-helpers';
interface Props {
marketId?: string;
noUpdate?: boolean;
assetDecimals: number;
}
export const MarketLiquiditySupplied = ({
marketId,
assetDecimals,
noUpdate = false,
}: Props) => {
const [market, setMarket] = useState<MarketData>();
const { params } = useNetworkParams([
NetworkParams.market_liquidity_stakeToCcySiskas,
NetworkParams.market_liquidity_targetstake_triggering_ratio,
]);
const stakeToCcyVolume = Number(params.market_liquidity_stakeToCcySiskas);
const triggeringRatio = Number(
params.market_liquidity_targetstake_triggering_ratio
);
const variables = useMemo(
() => ({
marketId: marketId,
}),
[marketId]
);
const { data } = useDataProvider<SingleMarketFieldsFragment, never>({
dataProvider: marketProvider,
variables,
skip: !marketId,
});
const update = useCallback(
({ data: marketData }: { data: MarketData | null }) => {
if (!noUpdate && marketData) {
setMarket(marketData);
}
return true;
},
[noUpdate]
);
useDataProvider<MarketData, MarketDataUpdateFieldsFragment>({
dataProvider: marketDataProvider,
update,
variables,
skip: noUpdate || !marketId || !data,
});
const supplied = market?.suppliedStake
? addDecimalsFormatNumber(
new BigNumber(market?.suppliedStake)
.multipliedBy(stakeToCcyVolume || 1)
.toString(),
assetDecimals
)
: '-';
const { percentage } = useCheckLiquidityStatus({
suppliedStake: market?.suppliedStake || 0,
targetStake: market?.targetStake || 0,
triggeringRatio,
});
const compiledGrid = [
{
label: t('Supplied stake'),
value: market?.suppliedStake
? addDecimalsFormatNumber(
new BigNumber(market?.suppliedStake).toString(),
assetDecimals
)
: '-',
},
{
label: t('Target stake'),
value: market?.targetStake
? addDecimalsFormatNumber(
new BigNumber(market?.targetStake).toString(),
assetDecimals
)
: '-',
},
];
const description = (
<section>
{compiledGrid && <DataGrid grid={compiledGrid} />}
<br />
<Link href={`/#/liquidity/${marketId}`} data-testid="view-liquidity-link">
{t('View liquidity provision table')}
</Link>
</section>
);
return (
<HeaderStat
heading={t('Liquidity supplied')}
description={description}
testId="liquidity-supplied"
>
{/* <Indicator variant={status} /> */}
{supplied} ({formatNumberPercentage(percentage, 2)})
</HeaderStat>
);
};
@@ -1,4 +1,4 @@
import React, { useCallback } from 'react';
import React, { useMemo, useState, useCallback } from 'react';
import { useLocation } from 'react-router-dom';
import { Dialog } from '@vegaprotocol/ui-toolkit';
import {
@@ -12,50 +12,59 @@ import * as constants from '../constants';
import { RiskNoticeDialog } from './risk-notice-dialog';
import { WelcomeNoticeDialog } from './welcome-notice-dialog';
import { WelcomeLandingDialog } from './welcome-landing-dialog';
import { useGlobalStore } from '../../stores';
interface DialogConfig {
open?: boolean;
content: React.ReactNode;
title?: string;
size?: 'small' | 'medium';
onClose: () => void;
}
export const WelcomeDialog = () => {
const { pathname } = useLocation();
const { VEGA_ENV } = useEnvironment();
let dialogContent: React.ReactNode = null;
let title = '';
let size: 'small' | 'medium' = 'small';
const [dialog, setDialog] = useState<DialogConfig | null>(null);
const onClose = useCallback(() => {
setDialog(null);
}, [setDialog]);
const [riskAccepted] = useLocalStorage(constants.RISK_ACCEPTED_KEY);
const { data } = useDataProvider({
dataProvider: activeMarketsProvider,
});
const { update, shouldDisplayWelcomeDialog } = useGlobalStore((store) => ({
update: store.update,
shouldDisplayWelcomeDialog: store.shouldDisplayWelcomeDialog,
}));
const isRiskDialogNeeded =
riskAccepted !== 'true' && VEGA_ENV === Networks.MAINNET;
const isWelcomeDialogNeeded = pathname === '/' || shouldDisplayWelcomeDialog;
const onClose = useCallback(() => {
update({ shouldDisplayWelcomeDialog: isRiskDialogNeeded });
// eslint-disable-next-line react-hooks/exhaustive-deps
dialogContent = null;
}, [update, isRiskDialogNeeded]);
if (isRiskDialogNeeded) {
dialogContent = <RiskNoticeDialog onClose={onClose} />;
title = t('WARNING');
size = 'medium';
} else if (isWelcomeDialogNeeded && data?.length === 0) {
dialogContent = <WelcomeNoticeDialog />;
} else if (isWelcomeDialogNeeded && (data?.length || 0) > 0) {
dialogContent = <WelcomeLandingDialog onClose={onClose} />;
}
return (
useMemo(() => {
switch (true) {
case riskAccepted !== 'true' && VEGA_ENV === Networks.MAINNET:
setDialog({
content: <RiskNoticeDialog onClose={onClose} />,
title: t('WARNING'),
size: 'medium',
onClose,
});
break;
case pathname === '/' && data?.length === 0:
setDialog({
content: <WelcomeNoticeDialog />,
onClose,
});
break;
case pathname === '/' && (data?.length || 0) > 0:
setDialog({
content: <WelcomeLandingDialog onClose={onClose} />,
onClose,
});
break;
}
}, [onClose, data?.length, riskAccepted, pathname, VEGA_ENV, setDialog]);
return dialog ? (
<Dialog
open={Boolean(dialogContent)}
title={title}
size={size}
onChange={onClose}
open={Boolean(dialog.content)}
title={dialog.title}
size={dialog.size}
onChange={dialog.onClose}
>
{dialogContent}
{dialog.content}
</Dialog>
);
) : null;
};
@@ -12,6 +12,7 @@ import {
} from '../select-market';
import { WelcomeDialogHeader } from './welcome-dialog-header';
import { Link, useNavigate, useParams } from 'react-router-dom';
import { useGlobalStore } from '../../stores';
import { ProposedMarkets } from './proposed-markets';
import { Links, Routes } from '../../pages/client-router';
@@ -26,13 +27,18 @@ export const SelectMarketLandingTable = ({
const navigate = useNavigate();
const marketId = params.marketId;
const { update } = useGlobalStore((store) => ({
update: store.update,
}));
const onSelect = useCallback(
(id: string) => {
if (id && id !== marketId) {
update({ marketId: id });
navigate(Links[Routes.MARKET](id));
}
},
[marketId, navigate]
[marketId, update, navigate]
);
const onSelectMarket = useCallback(
+2 -2
View File
@@ -3,7 +3,7 @@ import type { RouteObject } from 'react-router-dom';
import { useRoutes } from 'react-router-dom';
import dynamic from 'next/dynamic';
import { t } from '@vegaprotocol/react-helpers';
import { Loader, Splash } from '@vegaprotocol/ui-toolkit';
import { Splash } from '@vegaprotocol/ui-toolkit';
import trimEnd from 'lodash/trimEnd';
const LazyHome = dynamic(() => import('../client-pages/home'), {
@@ -91,7 +91,7 @@ export const ClientRouter = () => {
<Suspense
fallback={
<div className="w-full h-full flex justify-center items-center">
<Loader />
{t('Loading...')}
</div>
}
>
+4 -11
View File
@@ -1,12 +1,10 @@
import { LocalStorage } from '@vegaprotocol/react-helpers';
import create from 'zustand';
import produce from 'immer';
interface GlobalStore {
networkSwitcherDialog: boolean;
marketId: string | null;
update: (store: Partial<Omit<GlobalStore, 'update'>>) => void;
shouldDisplayWelcomeDialog: boolean;
}
interface PageTitleStore {
@@ -17,15 +15,10 @@ interface PageTitleStore {
export const useGlobalStore = create<GlobalStore>((set) => ({
networkSwitcherDialog: false,
marketId: LocalStorage.getItem('marketId') || null,
shouldDisplayWelcomeDialog: false,
update: (newState) => {
set(
produce((state: GlobalStore) => {
Object.assign(state, newState);
})
);
if (newState.marketId) {
LocalStorage.setItem('marketId', newState.marketId);
update: (state) => {
set(state);
if (state.marketId) {
LocalStorage.setItem('marketId', state.marketId);
}
},
}));
+1 -1
View File
@@ -213,7 +213,7 @@ export const AssetDetailsTable = ({
}: AssetDetailsTableProps) => {
const longStringModifiers = (key: AssetDetail, value: string) =>
(value && key === AssetDetail.CONTRACT_ADDRESS) || key === AssetDetail.ID
? { className: 'break-all', title: value }
? { className: 'truncate', title: value }
: {};
const details = rows.map((r) => ({
@@ -6,10 +6,10 @@ import {
Tooltip,
} from '@vegaprotocol/ui-toolkit';
import * as Schema from '@vegaprotocol/types';
import { DataGrid, t } from '@vegaprotocol/react-helpers';
import { t } from '@vegaprotocol/react-helpers';
import { timeInForceLabel } from '@vegaprotocol/orders';
import type { MarketDealTicket } from '@vegaprotocol/market-list';
import { compileGridData } from '../trading-mode-tooltip';
import { compileGridData, MarketDataGrid } from '../trading-mode-tooltip';
import { MarketModeValidationType } from '../../constants';
interface TimeInForceSelectorProps {
@@ -78,7 +78,9 @@ export const TimeInForceSelector = ({
return (
<span>
{t('This market is in auction until it reaches')}{' '}
<Tooltip description={<DataGrid grid={compileGridData(market)} />}>
<Tooltip
description={<MarketDataGrid grid={compileGridData(market)} />}
>
<span>{t('sufficient liquidity')}</span>
</Tooltip>
{'. '}
@@ -93,7 +95,9 @@ export const TimeInForceSelector = ({
return (
<span>
{t('This market is in auction due to')}{' '}
<Tooltip description={<DataGrid grid={compileGridData(market)} />}>
<Tooltip
description={<MarketDataGrid grid={compileGridData(market)} />}
>
<span>{t('high price volatility')}</span>
</Tooltip>
{'. '}
@@ -1,9 +1,9 @@
import { FormGroup, InputError, Tooltip } from '@vegaprotocol/ui-toolkit';
import { DataGrid, t } from '@vegaprotocol/react-helpers';
import { t } from '@vegaprotocol/react-helpers';
import * as Schema from '@vegaprotocol/types';
import { Toggle } from '@vegaprotocol/ui-toolkit';
import type { MarketDealTicket } from '@vegaprotocol/market-list';
import { compileGridData } from '../trading-mode-tooltip';
import { compileGridData, MarketDataGrid } from '../trading-mode-tooltip';
import { MarketModeValidationType } from '../../constants';
interface TypeSelectorProps {
@@ -33,7 +33,9 @@ export const TypeSelector = ({
return (
<span>
{t('This market is in auction until it reaches')}{' '}
<Tooltip description={<DataGrid grid={compileGridData(market)} />}>
<Tooltip
description={<MarketDataGrid grid={compileGridData(market)} />}
>
<span>{t('sufficient liquidity')}</span>
</Tooltip>
{'. '}
@@ -46,7 +48,9 @@ export const TypeSelector = ({
return (
<span>
{t('This market is in auction due to')}{' '}
<Tooltip description={<DataGrid grid={compileGridData(market)} />}>
<Tooltip
description={<MarketDataGrid grid={compileGridData(market)} />}
>
<span>{t('high price volatility')}</span>
</Tooltip>
{'. '}
@@ -1,4 +1,3 @@
import type { DataGridProps } from '@vegaprotocol/react-helpers';
import {
t,
getDateTimeFormat,
@@ -7,6 +6,7 @@ import {
import * as Schema from '@vegaprotocol/types';
import { Link as UILink } from '@vegaprotocol/ui-toolkit';
import type { ReactNode } from 'react';
import type { MarketDataGridProps } from './market-data-grid';
import { Link } from 'react-router-dom';
import type { MarketDealTicket } from '@vegaprotocol/market-list';
@@ -14,7 +14,7 @@ export const compileGridData = (
market: MarketDealTicket,
onSelect?: (id: string) => void
): { label: ReactNode; value?: ReactNode }[] => {
const grid: DataGridProps['grid'] = [];
const grid: MarketDataGridProps['grid'] = [];
const isLiquidityMonitoringAuction =
market.data.marketTradingMode ===
Schema.MarketTradingMode.TRADING_MODE_MONITORING_AUCTION &&
@@ -1,2 +1,3 @@
export * from './market-data-grid';
export * from './trading-mode-tooltip';
export * from './compile-grid-data';
@@ -1,13 +1,13 @@
import type { ReactNode } from 'react';
export type DataGridProps = {
export type MarketDataGridProps = {
grid: {
label: string | ReactNode;
value?: ReactNode;
}[];
};
export const DataGrid = ({ grid }: DataGridProps) => {
export const MarketDataGrid = ({ grid }: MarketDataGridProps) => {
return (
<>
{grid.map(
@@ -1,10 +1,11 @@
import type { ReactNode } from 'react';
import classNames from 'classnames';
import { useEnvironment } from '@vegaprotocol/environment';
import { DataGrid, t } from '@vegaprotocol/react-helpers';
import { t } from '@vegaprotocol/react-helpers';
import * as Schema from '@vegaprotocol/types';
import { ExternalLink } from '@vegaprotocol/ui-toolkit';
import { createDocsLinks } from '@vegaprotocol/react-helpers';
import { MarketDataGrid } from './market-data-grid';
type TradingModeTooltipProps = {
tradingMode: Schema.MarketTradingMode | null;
@@ -45,7 +46,7 @@ export const TradingModeTooltip = ({
</ExternalLink>
)}
</p>
{compiledGrid && <DataGrid grid={compiledGrid} />}
{compiledGrid && <MarketDataGrid grid={compiledGrid} />}
</section>
);
}
@@ -71,7 +72,7 @@ export const TradingModeTooltip = ({
</ExternalLink>
)}
</p>
{compiledGrid && <DataGrid grid={compiledGrid} />}
{compiledGrid && <MarketDataGrid grid={compiledGrid} />}
</section>
);
}
@@ -93,7 +94,7 @@ export const TradingModeTooltip = ({
</ExternalLink>
)}
</p>
{compiledGrid && <DataGrid grid={compiledGrid} />}
{compiledGrid && <MarketDataGrid grid={compiledGrid} />}
</section>
);
}
@@ -1,6 +1,3 @@
import { renderHook } from '@testing-library/react';
import { Intent } from '@vegaprotocol/ui-toolkit';
import BigNumber from 'bignumber.js';
import {
formatWithAsset,
sumLiquidityCommitted,
@@ -9,7 +6,6 @@ import {
getCandle24hAgo,
getChange,
EMPTY_VALUE,
useCheckLiquidityStatus,
} from './liquidity-utils';
const CANDLES_1 = [
@@ -122,50 +118,3 @@ describe('getChange', () => {
expect(result).toEqual(EMPTY_VALUE);
});
});
describe('useCheckLiquidityStatus', () => {
it('should return amber if liquidity is enough', () => {
const { result } = renderHook(() =>
useCheckLiquidityStatus({
suppliedStake: '60',
targetStake: '100',
triggeringRatio: '0.5',
})
);
expect(result.current).toEqual({
status: Intent.Warning,
percentage: new BigNumber('60'),
});
});
it('should return red if liquidity is not enough', () => {
const { result } = renderHook(() =>
useCheckLiquidityStatus({
suppliedStake: '60',
targetStake: '100',
triggeringRatio: '1',
})
);
expect(result.current).toEqual({
status: Intent.Danger,
percentage: new BigNumber('60'),
});
});
it('should return green if liquidity is enough', () => {
const { result } = renderHook(() =>
useCheckLiquidityStatus({
suppliedStake: '101',
targetStake: '100',
triggeringRatio: '1',
})
);
expect(result.current).toEqual({
status: Intent.Success,
percentage: new BigNumber('101'),
});
});
});
@@ -2,7 +2,6 @@ import BigNumber from 'bignumber.js';
import { addDecimalsFormatNumber } from '@vegaprotocol/react-helpers';
import type { MarketNodeFragment } from './../__generated__/MarketsLiquidity';
import { Intent } from '@vegaprotocol/ui-toolkit';
export type LiquidityProvisionMarket = MarketNodeFragment;
@@ -118,46 +117,3 @@ export const getTargetStake = (
) => {
return markets.find((m) => m.id === marketId)?.data?.targetStake || '0';
};
export const useCheckLiquidityStatus = ({
suppliedStake,
targetStake,
triggeringRatio,
}: {
suppliedStake: string | number;
targetStake: string | number;
triggeringRatio: string | number;
}): {
status: Intent;
percentage: BigNumber;
} => {
// percentage supplied
const percentage = new BigNumber(suppliedStake)
.dividedBy(targetStake)
.multipliedBy(100);
// IF supplied_stake >= target_stake THEN
if (new BigNumber(suppliedStake).gte(new BigNumber(targetStake))) {
// show a green status, e.g. "🟢 $13,666,999 liquidity supplied"
return {
status: Intent.Success,
percentage,
};
// ELSE IF supplied_stake > NETPARAM[market.liquidity.targetstake.triggering.ratio] * target_stake THEN
} else if (
new BigNumber(suppliedStake).gte(
new BigNumber(targetStake).multipliedBy(triggeringRatio)
)
) {
// show an amber status, e.g. "🟠 $3,456,123 liquidity supplied"
return {
status: Intent.Warning,
percentage,
};
// ELSE show a red status, e.g. "🔴 $600,002 liquidity supplied"
} else {
return {
status: Intent.Danger,
percentage,
};
}
};
+2 -4
View File
@@ -3,14 +3,14 @@ import * as Types from '@vegaprotocol/types';
import { gql } from '@apollo/client';
import * as Apollo from '@apollo/client';
const defaultOptions = {} as const;
export type MarketDataUpdateFieldsFragment = { __typename?: 'ObservableMarketData', marketId: string, bestBidPrice: string, bestOfferPrice: string, markPrice: string, trigger: Types.AuctionTrigger, staticMidPrice: string, marketTradingMode: Types.MarketTradingMode, marketState: Types.MarketState, indicativeVolume: string, indicativePrice: string, bestStaticBidPrice: string, bestStaticOfferPrice: string, targetStake?: string | null, suppliedStake?: string | null };
export type MarketDataUpdateFieldsFragment = { __typename?: 'ObservableMarketData', marketId: string, bestBidPrice: string, bestOfferPrice: string, markPrice: string, trigger: Types.AuctionTrigger, staticMidPrice: string, marketTradingMode: Types.MarketTradingMode, marketState: Types.MarketState, indicativeVolume: string, indicativePrice: string, bestStaticBidPrice: string, bestStaticOfferPrice: string };
export type MarketDataUpdateSubscriptionVariables = Types.Exact<{
marketId: Types.Scalars['ID'];
}>;
export type MarketDataUpdateSubscription = { __typename?: 'Subscription', marketsData: Array<{ __typename?: 'ObservableMarketData', marketId: string, bestBidPrice: string, bestOfferPrice: string, markPrice: string, trigger: Types.AuctionTrigger, staticMidPrice: string, marketTradingMode: Types.MarketTradingMode, marketState: Types.MarketState, indicativeVolume: string, indicativePrice: string, bestStaticBidPrice: string, bestStaticOfferPrice: string, targetStake?: string | null, suppliedStake?: string | null }> };
export type MarketDataUpdateSubscription = { __typename?: 'Subscription', marketsData: Array<{ __typename?: 'ObservableMarketData', marketId: string, bestBidPrice: string, bestOfferPrice: string, markPrice: string, trigger: Types.AuctionTrigger, staticMidPrice: string, marketTradingMode: Types.MarketTradingMode, marketState: Types.MarketState, indicativeVolume: string, indicativePrice: string, bestStaticBidPrice: string, bestStaticOfferPrice: string }> };
export type MarketDataFieldsFragment = { __typename?: 'MarketData', bestBidPrice: string, bestOfferPrice: string, markPrice: string, trigger: Types.AuctionTrigger, staticMidPrice: string, marketTradingMode: Types.MarketTradingMode, marketState: Types.MarketState, indicativeVolume: string, indicativePrice: string, bestStaticBidPrice: string, bestStaticOfferPrice: string, targetStake?: string | null, suppliedStake?: string | null, auctionStart?: string | null, auctionEnd?: string | null, market: { __typename?: 'Market', id: string } };
@@ -35,8 +35,6 @@ export const MarketDataUpdateFieldsFragmentDoc = gql`
indicativePrice
bestStaticBidPrice
bestStaticOfferPrice
targetStake
suppliedStake
}
`;
export const MarketDataFieldsFragmentDoc = gql`
@@ -11,8 +11,6 @@ fragment MarketDataUpdateFields on ObservableMarketData {
indicativePrice
bestStaticBidPrice
bestStaticOfferPrice
targetStake
suppliedStake
}
subscription MarketDataUpdate($marketId: ID!) {
@@ -31,7 +31,7 @@ const compileData = (data?: StatsQuery) => {
value.forEach((x) => {
const stat = {
...x,
value: statData || '-',
value: statData,
};
stat.promoted ? acc.promoted.push(stat) : acc.table.push(stat);
@@ -75,7 +75,7 @@ export const StatsManager = ({ className }: StatsManagerProps) => {
return (
<PromotedStatsItem
title={stat.title}
value={stat.value || '-'}
value={stat.value}
formatter={stat.formatter}
goodThreshold={stat.goodThreshold}
description={stat.description}
@@ -92,7 +92,7 @@ export const StatsManager = ({ className }: StatsManagerProps) => {
return (
<TableRow
title={stat.title}
value={stat.value || '-'}
value={stat.value}
formatter={stat.formatter}
goodThreshold={stat.goodThreshold}
description={stat.description}
+12 -6
View File
@@ -48,7 +48,13 @@ export const statsFields: { [key in keyof Stats]: StatFields[] } = {
description: t('The total number of nodes registered on the network'),
},
],
inactiveNodes: [],
inactiveNodes: [
{
title: t('Inactive nodes'),
goodThreshold: (totalInactive: number) => totalInactive < 1,
description: t('Nodes that are registered but not validating'),
},
],
stakedTotal: [
{
title: t('Total staked'),
@@ -168,11 +174,11 @@ export const statsFields: { [key in keyof Stats]: StatFields[] } = {
title: t('Uptime'),
formatter: (t: string) => {
if (!t) {
return '-';
return;
}
const date = new Date(t);
if (!isValidDate(date)) {
return '-';
return;
}
const secSinceStart = (new Date().getTime() - date.getTime()) / 1000;
const days = Math.floor(secSinceStart / 60 / 60 / 24);
@@ -188,13 +194,13 @@ export const statsFields: { [key in keyof Stats]: StatFields[] } = {
title: t('Up since'),
formatter: (t: string) => {
if (!t) {
return '-';
return;
}
const date = new Date(t);
if (!isValidDate(date)) {
return '-';
return;
}
return getDateTimeFormat().format(date) || '-';
return getDateTimeFormat().format(date);
},
description: t('Genesis'),
},
@@ -102,9 +102,6 @@ export const NetworkParams = {
spam_protection_voting_min_tokens: 'spam_protection_voting_min_tokens',
spam_protection_proposal_min_tokens: 'spam_protection_proposal_min_tokens',
market_liquidity_stakeToCcySiskas: 'market_liquidity_stakeToCcySiskas',
market_liquidity_stakeToCcyVolume: 'market_liquidity_stakeToCcyVolume',
market_liquidity_targetstake_triggering_ratio:
'market_liquidity_targetstake_triggering_ratio',
} as const;
type Params = typeof NetworkParams;
@@ -9,8 +9,6 @@ const Themes = {
type Theme = typeof Themes[keyof typeof Themes];
const isBrowser = typeof window !== 'undefined';
const validateTheme = (theme: string): theme is Theme => {
if (Object.values(Themes).includes(theme as Theme)) return true;
LocalStorage.removeItem(THEME_STORAGE_KEY);
@@ -18,7 +16,7 @@ const validateTheme = (theme: string): theme is Theme => {
};
const setThemeClassName = (theme: Theme) => {
if (isBrowser) {
if (typeof window !== 'undefined') {
if (theme === Themes.DARK) {
document.documentElement.classList.add(Themes.DARK);
} else {
@@ -28,13 +26,6 @@ const setThemeClassName = (theme: Theme) => {
};
const getCurrentTheme = () => {
// If an app is only dark theme then the page will be rendered with
// the dark class already applied. In this case return early with state
// set to dark
if (isBrowser && document.documentElement.classList.contains(Themes.DARK)) {
return Themes.DARK;
}
const storedTheme = LocalStorage.getItem(THEME_STORAGE_KEY);
if (storedTheme && validateTheme(storedTheme)) {
@@ -43,7 +34,7 @@ const getCurrentTheme = () => {
}
const theme =
isBrowser &&
typeof window !== 'undefined' &&
typeof window.matchMedia === 'function' && // jest test environment matchMedia is undefined
window.matchMedia('(prefers-color-scheme: dark)').matches
? Themes.DARK
-1
View File
@@ -14,4 +14,3 @@ export * from './lib/links';
export * from './lib/is-asset-erc20';
export * from './lib/remove-pagination-wrapper';
export * from './lib/__generated__/ChainId';
export * from './lib/data-grid';
@@ -1 +0,0 @@
export * from './data-grid';
-1
View File
@@ -11,4 +11,3 @@ export * from './remove-0x';
export * from './time';
export * from './links';
export * from './remove-pagination-wrapper';
export * from './data-grid';
@@ -34,7 +34,7 @@ export function Dialog({
);
const wrapperClasses = classNames(
// Positions the modal in the center of screen
'z-20 relative rounded top-[10vh]',
'z-20 relative rounded top-[10vh] max-w-[90vw]',
// Dimensions
'max-w-[90vw] p-4 md:p-8',
// Need to apply background and text colors again as content is rendered in a portal
+158 -65
View File
@@ -1,11 +1,74 @@
import { t } from '@vegaprotocol/react-helpers';
import { WalletClient } from '@vegaprotocol/wallet-client';
import { z } from 'zod';
import { clearConfig, getConfig, setConfig } from '../storage';
import { encodeTransaction } from '../utils';
import type { Transaction, VegaConnector } from './vega-connector';
import { WalletError } from './vega-connector';
const VERSION = 'v2';
enum Methods {
ConnectWallet = 'client.connect_wallet',
DisconnectWallet = 'client.disconnect_wallet',
ListKeys = 'client.list_keys',
SendTransaction = 'client.send_transaction',
GetChainId = 'client.get_chain_id',
}
const BaseSchema = z.object({
id: z.string(),
jsonrpc: z.literal('2.0'),
});
const ConnectWalletSchema = BaseSchema.extend({
result: z.object({
token: z.string(),
}),
});
const ListKeysSchema = BaseSchema.extend({
result: z.object({
keys: z.array(
z.object({
publicKey: z.string(),
name: z.string(),
})
),
}),
});
const GetChainIdSchema = BaseSchema.extend({
result: z.object({
chainID: z.string(),
}),
});
const SendTransactionSchema = BaseSchema.extend({
result: z.object({
receivedAt: z.string(),
sentAt: z.string(),
transactionHash: z.string(),
transaction: z.object({
signature: z.object({
value: z.string(),
}),
}),
}),
});
type JsonRpcError = {
message: string;
code: number;
data?: string;
};
type Response =
| z.infer<typeof ConnectWalletSchema>
| z.infer<typeof ListKeysSchema>
| z.infer<typeof GetChainIdSchema>
| z.infer<typeof SendTransactionSchema>
| { error: JsonRpcError };
export const ClientErrors = {
NO_SERVICE: new WalletError(t('No service'), 100),
NO_TOKEN: new WalletError(t('No token'), 101),
@@ -23,69 +86,51 @@ export const ClientErrors = {
),
} as const;
class NoClientError extends Error {
constructor() {
super(
t('No client found. The connector needs to be initialized with a url.')
);
}
}
export class JsonRpcConnector implements VegaConnector {
version = VERSION;
private _url: string | null = null;
url: string | null = null;
token: string | null = null;
reqId = 0;
client?: WalletClient;
constructor() {
const cfg = getConfig();
this.token = cfg?.token ?? null;
if (cfg && cfg.url) {
if (cfg) {
this.token = cfg.token;
this.url = cfg.url;
this.client = new WalletClient({
address: cfg.url,
token: cfg.token ?? undefined,
});
}
}
set url(url: string) {
this._url = url;
this.client = new WalletClient({
address: url,
token: this.token ?? undefined,
});
}
async getChainId() {
if (!this.client) {
throw new NoClientError();
const result = await this.request(Methods.GetChainId);
if ('error' in result) {
throw this.wrapError(result.error);
}
try {
const { result } = await this.client.GetChainId();
return result;
} catch (err) {
const parseResult = GetChainIdSchema.safeParse(result);
if (parseResult.success) {
return parseResult.data.result;
} else {
throw ClientErrors.INVALID_RESPONSE;
}
}
async connectWallet() {
if (!this.client) {
throw new NoClientError();
const result = await this.request(Methods.ConnectWallet, {
hostname: window.location.host,
});
if ('error' in result) {
throw this.wrapError(result.error);
}
const parseResult = ConnectWalletSchema.safeParse(result);
try {
const { result } = await this.client.ConnectWallet();
if (parseResult.success) {
// store token and other config for eager connect and subsequent requests
setConfig({
token: result.token,
token: parseResult.data.result.token,
connector: 'jsonRpc',
url: this.url,
});
return result;
} catch (err) {
return parseResult.data.result;
} else {
throw ClientErrors.INVALID_RESPONSE;
}
}
@@ -93,57 +138,80 @@ export class JsonRpcConnector implements VegaConnector {
// connect actually calling list_keys here, not to be confused with connect_wallet
// which retrieves the session token
async connect() {
if (!this.client) {
throw new NoClientError();
const cfg = getConfig();
if (!cfg?.token) {
throw ClientErrors.NO_TOKEN;
}
try {
const { result } = await this.client.ListKeys();
return result.keys;
} catch (err) {
const result = await this.request(Methods.ListKeys, {
token: cfg.token,
});
if ('error' in result) {
throw this.wrapError(result.error);
}
const parseResult = ListKeysSchema.safeParse(result);
if (parseResult.success) {
return parseResult.data.result.keys;
} else {
throw ClientErrors.INVALID_RESPONSE;
}
}
async disconnect() {
if (!this.client) {
throw new NoClientError();
const cfg = getConfig();
if (cfg?.token) {
await this.request(Methods.DisconnectWallet, {
token: cfg.token,
});
}
await this.client.DisconnectWallet();
clearConfig();
}
async sendTx(pubKey: string, transaction: Transaction) {
if (!this.client) {
throw new NoClientError();
const cfg = getConfig();
if (!cfg?.token) {
throw ClientErrors.NO_TOKEN;
}
try {
const { result } = await this.client.SendTransaction({
publicKey: pubKey,
sendingMode: 'TYPE_SYNC',
transaction,
});
const result = await this.request(Methods.SendTransaction, {
token: cfg.token,
publicKey: pubKey,
sendingMode: 'TYPE_SYNC',
encodedTransaction: encodeTransaction(transaction),
});
if ('error' in result) {
// In the case of sending a tx, error code 3001 indicates that the
// user rejected the tx. Returning null will allow the dialog to close immediately
if (result.error.code === 3001) {
return null;
} else {
throw this.wrapError(result.error);
}
}
const parsedResult = SendTransactionSchema.safeParse(result);
if (parsedResult.success) {
return {
transactionHash: result.transactionHash,
sentAt: result.sentAt,
receivedAt: result.receivedAt,
signature: result.transaction.signature.value,
transactionHash: parsedResult.data.result.transactionHash,
sentAt: parsedResult.data.result.sentAt,
receivedAt: parsedResult.data.result.receivedAt,
signature: parsedResult.data.result.transaction.signature.value,
};
} catch (err) {
} else {
throw ClientErrors.INVALID_RESPONSE;
}
}
async checkCompat() {
try {
const result = await fetch(`${this._url}/api/${this.version}/methods`);
const result = await fetch(`${this.url}/api/${this.version}/methods`);
if (!result.ok) {
const err = ClientErrors.INVALID_WALLET;
err.data = t(
`The wallet running at ${this._url} is not supported. Required version is ${this.version}`
`The wallet running at ${this.url} is not supported. Required version is ${this.version}`
);
throw err;
}
@@ -156,4 +224,29 @@ export class JsonRpcConnector implements VegaConnector {
throw ClientErrors.NO_SERVICE;
}
}
private async request(method: Methods, params?: object): Promise<Response> {
try {
const result = await fetch(`${this.url}/api/${this.version}/requests`, {
method: 'post',
body: JSON.stringify({
jsonrpc: '2.0',
method,
params,
id: `${this.reqId++}`,
}),
headers: {
'Content-Type': 'application/json',
},
});
const json = await result.json();
return json;
} catch (err) {
throw ClientErrors.NO_SERVICE;
}
}
private wrapError(error: JsonRpcError) {
return new WalletError(error.message, error.code, error.data);
}
}
+25 -44
View File
@@ -76,13 +76,13 @@ interface ProposalNewMarketTerms {
changes: {
decimalPlaces: string;
positionDecimalPlaces: string;
lpPriceRange: string;
instrument: {
name: string;
code: string;
future: {
settlementAsset: string;
quoteName: string;
settlementPriceDecimals: number;
dataSourceSpecForSettlementData: DataSourceSpec;
dataSourceSpecForTradingTermination: DataSourceSpec;
dataSourceSpecBinding: DataSourceSpecBinding;
@@ -100,6 +100,12 @@ interface ProposalNewMarketTerms {
};
logNormal: LogNormal;
};
liquidityCommitment: {
commitmentAmount: string;
fee: string;
buys: Buy[];
sells: Buy[];
};
};
closingTimestamp: number;
enactmentTimestamp: number;
@@ -178,66 +184,35 @@ interface ProposalUpdateAssetTerms {
}
interface DataSourceSpecBinding {
settlementDataProperty: string;
settlementPriceProperty: string;
tradingTerminationProperty: string;
}
interface InternalDataSourceSpec {
internal: {
time: {
conditions: Condition[];
};
interface DataSourceSpec {
config: {
signers: Signer[];
filters: Filter[];
};
}
interface ExternalDataSourceSpec {
external: {
oracle: {
signers: Signer[];
filters: Filter[];
};
};
}
type DataSourceSpec = InternalDataSourceSpec | ExternalDataSourceSpec;
type Signer =
| {
ethAddress: {
address: string;
};
address: string;
}
| {
pubKey: {
key: string;
};
key: string;
};
interface Filter {
key: DefaultFilterKey | IntegerFilterKey;
key: {
name: string;
type: string;
};
conditions?: Condition[];
}
interface DefaultFilterKey {
name: string;
type: 'TYPE_DECIMAL' | 'TYPE_BOOLEAN' | 'TYPE_TIMESTAMP' | 'TYPE_STRING';
}
interface IntegerFilterKey {
name: string;
type: 'TYPE_INTEGER';
numberDecimalPlaces: string;
}
type ConditionOperator =
| 'OPERATOR_EQUALS'
| 'OPERATOR_GREATER_THAN'
| 'OPERATOR_GREATER_THAN_OR_EQUAL'
| 'OPERATOR_LESS_THAN'
| 'OPERATOR_LESS_THAN_OR_EQUAL';
interface Condition {
operator: ConditionOperator;
operator: string;
value: string;
}
@@ -261,6 +236,12 @@ interface Trigger {
auctionExtension: string;
}
interface Buy {
offset: string;
proportion: number;
reference: string;
}
export interface ProposalSubmission {
rationale: {
description: string;
+1 -1
View File
@@ -17,7 +17,7 @@ export interface VegaWalletContextShape {
connect: (connector: VegaConnector) => Promise<PubKey[] | null>;
/** Disconnects from the connector and clears public key state */
disconnect: () => Promise<void>;
disconnect: () => Promise<boolean>;
/** Sets the current selected public key */
selectPubKey: (pubKey: string) => void;
+12 -8
View File
@@ -59,19 +59,23 @@ export const VegaWalletProvider = ({ children }: VegaWalletProviderProps) => {
}, []);
const disconnect = useCallback(async () => {
// always clear state after attempted disconnection.. this
// is because long lived token sessions (used in tests)
// cannot be cleared. Clearing state will force user to reconnect
// again as expected
setPubKeys(null);
setPubKey(null);
LocalStorage.removeItem(WALLET_KEY);
try {
await connector.current?.disconnect();
setPubKeys(null);
setPubKey(null);
connector.current = null;
LocalStorage.removeItem(WALLET_KEY);
return true;
} catch (err) {
console.error(err);
connector.current = null;
if (err instanceof WalletError && err.code === 100) {
setPubKeys(null);
setPubKey(null);
connector.current = null;
LocalStorage.removeItem(WALLET_KEY);
return true;
}
return false;
}
}, []);
-1
View File
@@ -36,7 +36,6 @@
"@sentry/nextjs": "^6.19.3",
"@sentry/react": "^6.19.2",
"@sentry/tracing": "^6.19.2",
"@vegaprotocol/wallet-client": "0.1.4",
"@walletconnect/ethereum-provider": "^1.7.5",
"@web3-react/core": "8.0.20-beta.0",
"@web3-react/metamask": "8.0.16-beta.0",
+2 -11
View File
@@ -7559,15 +7559,6 @@
"@typescript-eslint/types" "5.40.0"
eslint-visitor-keys "^3.3.0"
"@vegaprotocol/wallet-client@0.1.4":
version "0.1.4"
resolved "https://registry.yarnpkg.com/@vegaprotocol/wallet-client/-/wallet-client-0.1.4.tgz#202fa1a84dbef57199810383f2887a7ee0afd64c"
integrity sha512-uGEbusoi3lwyl7Nn9ovBg9YHrfcH/Rl33KUcLfdMeTX8FZO+n7BVm3ejd00e5RsM/PJlqJ1oW4qkiq7kervxng==
dependencies:
express "4.18.2"
nanoid "3.3.4"
node-fetch "2.6.7"
"@walletconnect/browser-utils@^1.8.0":
version "1.8.0"
resolved "https://registry.yarnpkg.com/@walletconnect/browser-utils/-/browser-utils-1.8.0.tgz#33c10e777aa6be86c713095b5206d63d32df0951"
@@ -12807,7 +12798,7 @@ expect@^29.0.0:
jest-message-util "^29.1.2"
jest-util "^29.1.2"
express@4.18.2, express@^4.17.1, express@^4.17.3:
express@^4.17.1, express@^4.17.3:
version "4.18.2"
resolved "https://registry.yarnpkg.com/express/-/express-4.18.2.tgz#3fabe08296e930c796c19e3c516979386ba9fd59"
integrity sha512-5/PsL6iGPdfQ/lKM1UuielYgv3BUoJfz1aUwU9vHZ+J7gyvwdQXFEBIEIaxeGf0GIcreATNyBExtalisDbuMqQ==
@@ -17342,7 +17333,7 @@ nan@^2.12.1:
resolved "https://registry.yarnpkg.com/nan/-/nan-2.17.0.tgz#c0150a2368a182f033e9aa5195ec76ea41a199cb"
integrity sha512-2ZTgtl0nJsO0KQCjEpxcIr5D+Yv90plTitZt9JBfQvVJDS5seMl3FOvsh3+9CoYWXf/1l5OaZzzF6nDm4cagaQ==
nanoid@3.3.4, nanoid@^3.3.1, nanoid@^3.3.4:
nanoid@^3.3.1, nanoid@^3.3.4:
version "3.3.4"
resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.3.4.tgz#730b67e3cd09e2deacf03c027c81c9d9dbc5e8ab"
integrity sha512-MqBkQh/OHTS2egovRtLk45wEyNXwF+cokD+1YPf9u5VfJiRdAiRwB2froX5Co9Rh20xs4siNPm8naNotSD6RBw==