Parameterize chain info using ethereum-lists/chains submodule
This commit is contained in:
parent
6e9db8a145
commit
88926bd777
|
@ -113,6 +113,40 @@ server {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
location /chains {
|
||||||
|
root /usr/share/nginx/html;
|
||||||
|
expires 30d;
|
||||||
|
|
||||||
|
# Base on: https://michielkalkman.com/snippets/nginx-cors-open-configuration/
|
||||||
|
if ($request_method = 'OPTIONS') {
|
||||||
|
add_header 'Access-Control-Allow-Origin' '*';
|
||||||
|
#
|
||||||
|
# Om nom nom cookies
|
||||||
|
#
|
||||||
|
add_header 'Access-Control-Allow-Credentials' 'true';
|
||||||
|
add_header 'Access-Control-Allow-Methods' 'GET, OPTIONS';
|
||||||
|
|
||||||
|
#
|
||||||
|
# Custom headers and headers various browsers *should* be OK with but aren't
|
||||||
|
#
|
||||||
|
add_header 'Access-Control-Allow-Headers' 'DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type';
|
||||||
|
|
||||||
|
#
|
||||||
|
# Tell client that this pre-flight info is valid for 20 days
|
||||||
|
#
|
||||||
|
add_header 'Access-Control-Max-Age' 1728000;
|
||||||
|
add_header 'Content-Type' 'text/plain charset=UTF-8';
|
||||||
|
add_header 'Content-Length' 0;
|
||||||
|
return 204;
|
||||||
|
}
|
||||||
|
if ($request_method = 'GET') {
|
||||||
|
add_header 'Access-Control-Allow-Origin' '*' always;
|
||||||
|
add_header 'Access-Control-Allow-Credentials' 'true' always;
|
||||||
|
add_header 'Access-Control-Allow-Methods' 'GET, OPTIONS' always;
|
||||||
|
add_header 'Access-Control-Allow-Headers' 'DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type' always;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
location / {
|
location / {
|
||||||
root /usr/share/nginx/html;
|
root /usr/share/nginx/html;
|
||||||
index index.html;
|
index index.html;
|
||||||
|
|
|
@ -52,8 +52,8 @@
|
||||||
"test": "craco test",
|
"test": "craco test",
|
||||||
"eject": "react-scripts eject",
|
"eject": "react-scripts eject",
|
||||||
"source-map-explorer": "source-map-explorer build/static/js/*.js",
|
"source-map-explorer": "source-map-explorer build/static/js/*.js",
|
||||||
"assets-start": "docker run --rm -p 3001:80 --name otterscan-assets -d -v$(pwd)/4bytes/signatures:/usr/share/nginx/html/signatures/ -v$(pwd)/trustwallet/blockchains/ethereum/assets:/usr/share/nginx/html/assets/1 -v$(pwd)/topic0/with_parameter_names:/usr/share/nginx/html/topic0/ -v$(pwd)/nginx/nginx.conf:/etc/nginx/nginx.conf -v$(pwd)/nginx/conf.d/default.conf:/etc/nginx/conf.d/default.conf nginx:1.21.1-alpine",
|
"assets-start": "docker run --rm -p 3001:80 --name otterscan-assets -d -v$(pwd)/4bytes/signatures:/usr/share/nginx/html/signatures/ -v$(pwd)/trustwallet/blockchains/ethereum/assets:/usr/share/nginx/html/assets/1 -v$(pwd)/topic0/with_parameter_names:/usr/share/nginx/html/topic0/ -v$(pwd)/chains/_data/chains:/usr/share/nginx/html/chains/ -v$(pwd)/nginx/nginx.conf:/etc/nginx/nginx.conf -v$(pwd)/nginx/conf.d/default.conf:/etc/nginx/conf.d/default.conf nginx:1.21.1-alpine",
|
||||||
"assets-start-with-param-names": "docker run --rm -p 3001:80 --name otterscan-assets -d -v$(pwd)/4bytes/with_parameter_names:/usr/share/nginx/html/signatures/ -v$(pwd)/trustwallet/blockchains/ethereum/assets:/usr/share/nginx/html/assets/1 -v$(pwd)/topic0/with_parameter_names:/usr/share/nginx/html/topic0/ -v$(pwd)/nginx/nginx.conf:/etc/nginx/nginx.conf -v$(pwd)/nginx/conf.d/default.conf:/etc/nginx/conf.d/default.conf nginx:1.21.1-alpine",
|
"assets-start-with-param-names": "docker run --rm -p 3001:80 --name otterscan-assets -d -v$(pwd)/4bytes/with_parameter_names:/usr/share/nginx/html/signatures/ -v$(pwd)/trustwallet/blockchains/ethereum/assets:/usr/share/nginx/html/assets/1 -v$(pwd)/topic0/with_parameter_names:/usr/share/nginx/html/topic0/ -v$(pwd)/chains/_data/chains:/usr/share/nginx/html/chains/ -v$(pwd)/nginx/nginx.conf:/etc/nginx/nginx.conf -v$(pwd)/nginx/conf.d/default.conf:/etc/nginx/conf.d/default.conf nginx:1.21.1-alpine",
|
||||||
"assets-stop": "docker stop otterscan-assets",
|
"assets-stop": "docker stop otterscan-assets",
|
||||||
"docker-build": "DOCKER_BUILDKIT=1 docker build -t otterscan -f Dockerfile .",
|
"docker-build": "DOCKER_BUILDKIT=1 docker build -t otterscan -f Dockerfile .",
|
||||||
"docker-start": "docker run --rm -p 5000:80 --name otterscan -d otterscan",
|
"docker-start": "docker run --rm -p 5000:80 --name otterscan -d otterscan",
|
||||||
|
|
|
@ -7,7 +7,7 @@ import ConnectionErrorPanel from "./ConnectionErrorPanel";
|
||||||
import Footer from "./Footer";
|
import Footer from "./Footer";
|
||||||
import { ConnectionStatus } from "./types";
|
import { ConnectionStatus } from "./types";
|
||||||
import { RuntimeContext, useRuntime } from "./useRuntime";
|
import { RuntimeContext, useRuntime } from "./useRuntime";
|
||||||
import { ChainInfoContext, defaultChainInfo } from "./useChainInfo";
|
import { ChainInfoContext, useChainInfoFromMetadataFile } from "./useChainInfo";
|
||||||
|
|
||||||
const Block = React.lazy(
|
const Block = React.lazy(
|
||||||
() => import(/* webpackChunkName: "block", webpackPrefetch: true */ "./Block")
|
() => import(/* webpackChunkName: "block", webpackPrefetch: true */ "./Block")
|
||||||
|
@ -41,17 +41,19 @@ const PageNotFound = React.lazy(
|
||||||
|
|
||||||
const App = () => {
|
const App = () => {
|
||||||
const runtime = useRuntime();
|
const runtime = useRuntime();
|
||||||
|
const chainInfo = useChainInfoFromMetadataFile(runtime);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Suspense fallback={null}>
|
<Suspense fallback={null}>
|
||||||
{runtime.connStatus !== ConnectionStatus.CONNECTED ? (
|
{runtime.connStatus !== ConnectionStatus.CONNECTED ||
|
||||||
|
chainInfo === undefined ? (
|
||||||
<ConnectionErrorPanel
|
<ConnectionErrorPanel
|
||||||
connStatus={runtime.connStatus}
|
connStatus={runtime.connStatus}
|
||||||
config={runtime.config}
|
config={runtime.config}
|
||||||
/>
|
/>
|
||||||
) : (
|
) : (
|
||||||
<RuntimeContext.Provider value={runtime}>
|
<RuntimeContext.Provider value={runtime}>
|
||||||
<ChainInfoContext.Provider value={defaultChainInfo}>
|
<ChainInfoContext.Provider value={chainInfo}>
|
||||||
<div className="h-screen flex flex-col">
|
<div className="h-screen flex flex-col">
|
||||||
<WarningHeader />
|
<WarningHeader />
|
||||||
<Router>
|
<Router>
|
||||||
|
|
|
@ -15,6 +15,11 @@ export const tokenLogoURL = (
|
||||||
address: string
|
address: string
|
||||||
): string => `${assetsURLPrefix}/assets/${chainId}/${address}/logo.png`;
|
): string => `${assetsURLPrefix}/assets/${chainId}/${address}/logo.png`;
|
||||||
|
|
||||||
|
export const chainInfoURL = (
|
||||||
|
assetsURLPrefix: string,
|
||||||
|
chainId: number
|
||||||
|
): string => `${assetsURLPrefix}/chains/eip155-${chainId}.json`;
|
||||||
|
|
||||||
export const blockURL = (blockNum: BlockTag) => `/block/${blockNum}`;
|
export const blockURL = (blockNum: BlockTag) => `/block/${blockNum}`;
|
||||||
|
|
||||||
export const blockTxsURL = (blockNum: BlockTag) => `/block/${blockNum}/txs`;
|
export const blockTxsURL = (blockNum: BlockTag) => `/block/${blockNum}/txs`;
|
||||||
|
|
|
@ -1,4 +1,6 @@
|
||||||
import { createContext, useContext } from "react";
|
import { createContext, useContext, useEffect, useState } from "react";
|
||||||
|
import { chainInfoURL } from "./url";
|
||||||
|
import { OtterscanRuntime } from "./useRuntime";
|
||||||
|
|
||||||
export type ChainInfo = {
|
export type ChainInfo = {
|
||||||
nativeName: string;
|
nativeName: string;
|
||||||
|
@ -14,6 +16,40 @@ export const defaultChainInfo: ChainInfo = {
|
||||||
|
|
||||||
export const ChainInfoContext = createContext<ChainInfo | undefined>(undefined);
|
export const ChainInfoContext = createContext<ChainInfo | undefined>(undefined);
|
||||||
|
|
||||||
|
export const useChainInfoFromMetadataFile = (
|
||||||
|
runtime: OtterscanRuntime | undefined
|
||||||
|
): ChainInfo | undefined => {
|
||||||
|
const assetsURLPrefix = runtime?.config?.assetsURLPrefix;
|
||||||
|
const chainId = runtime?.provider?.network.chainId;
|
||||||
|
|
||||||
|
const [chainInfo, setChainInfo] = useState<ChainInfo | undefined>(undefined);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
if (chainId === undefined) {
|
||||||
|
setChainInfo(undefined);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const readChainInfo = async () => {
|
||||||
|
const res = await fetch(chainInfoURL(assetsURLPrefix!, chainId));
|
||||||
|
if (!res.ok) {
|
||||||
|
setChainInfo(defaultChainInfo);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const info = await res.json();
|
||||||
|
|
||||||
|
setChainInfo({
|
||||||
|
nativeName: info.nativeCurrency.name,
|
||||||
|
nativeDecimals: info.nativeCurrency.decimals,
|
||||||
|
nativeSymbol: info.nativeCurrency.symbol,
|
||||||
|
});
|
||||||
|
};
|
||||||
|
readChainInfo();
|
||||||
|
}, [assetsURLPrefix, chainId]);
|
||||||
|
|
||||||
|
return chainInfo;
|
||||||
|
};
|
||||||
|
|
||||||
export const useChainInfo = (): ChainInfo => {
|
export const useChainInfo = (): ChainInfo => {
|
||||||
const chainInfo = useContext(ChainInfoContext);
|
const chainInfo = useContext(ChainInfoContext);
|
||||||
if (chainInfo === undefined) {
|
if (chainInfo === undefined) {
|
||||||
|
|
Loading…
Reference in New Issue