cyb/src/contexts/appData.tsx

import React, { useContext, useEffect, useMemo, useRef, useState } from 'react';
import useQueryContract from 'src/hooks/contract/useQueryContract';
import useGetMarketData from 'src/hooks/useGetMarketData';
import useConvertMarketData from 'src/hooks/warp/useConvertMarketData';
import { ObjKeyValue } from 'src/types/data';
import { useWebsockets } from 'src/websockets/context';

type OptionObj<T> = T | object;

type ObjData = OptionObj<ObjKeyValue>;

type DataProviderContextType = {
  marketData: ObjData;
  dataTotalSupply: ObjData;
  block: number | null;
  filterParticles: string[];
};

const valueContext = {
  marketData: {},
  dataTotalSupply: {},
  block: null,
  filterParticles: [],
};

export const FILTERING_CONTRACT =
  'bostrom1p8drdvmwygrreesp4e425q6xs77zkcsj7z7h9as7sketuv5w334slsxv7l';

const DataProviderContext = React.createContext<DataProviderContextType>(valueContext);

export function useAppData() {
  return useContext(DataProviderContext);
}

function DataProvider({ children }: { children: React.ReactNode }) {
  const { marketData, dataTotal } = useGetMarketData();
  const convertMarketData = useConvertMarketData(marketData);
  const { cyber } = useWebsockets();
  const [blockHeight, setBlockHeight] = useState<number | null>(null);

  const filterContractQuery = useQueryContract(FILTERING_CONTRACT, {
    particles: {},
  });

  const filterParticlesRaw = filterContractQuery?.data?.map((item) => item[1]);
  const filterParticlesRef = useRef<string[]>([]);
  if (filterParticlesRaw && JSON.stringify(filterParticlesRaw) !== JSON.stringify(filterParticlesRef.current)) {
    filterParticlesRef.current = filterParticlesRaw;
  }
  const filterParticles = filterParticlesRef.current;

  const resultMarketData = Object.keys(convertMarketData).length ? convertMarketData : marketData;

  useEffect(() => {
    if (!cyber?.connected) {
      return;
    }

    const param = "tm.event='NewBlockHeader'";

    if (cyber.subscriptions.includes(param)) {
      return;
    }

    cyber.sendMessage({
      method: 'subscribe',
      params: [param],
      id: '1',
      jsonrpc: '2.0',
    });
  }, [cyber?.connected, cyber?.sendMessage, cyber?.subscriptions]);

  useEffect(() => {
    if (!cyber?.message?.result) {
      return;
    }

    const message = cyber?.message;

    if (
      Object.keys(message.result).length > 0 &&
      message.result.data.type === 'tendermint/event/NewBlockHeader'
    ) {
      const { height } = message.result.data.value.header;
      setBlockHeight(height);
    }
  }, [cyber?.message]);

  const valueMemo = useMemo(
    () => ({
      marketData: resultMarketData,
      dataTotalSupply: dataTotal,
      block: blockHeight,
      filterParticles,
    }),
    [resultMarketData, dataTotal, blockHeight, filterParticles]
  );

  return <DataProviderContext.Provider value={valueMemo}>{children}</DataProviderContext.Provider>;
}

export default DataProvider;

Synonyms

pussy-ts/src/contexts/appData.tsx

Neighbours