@edgeandnode/graph-auth-kit 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +238 -0
- package/dist/Components/ConnectModal.d.ts +2 -0
- package/dist/Components/ConnectModal.d.ts.map +1 -0
- package/dist/Components/ConnectorOption.d.ts +13 -0
- package/dist/Components/ConnectorOption.d.ts.map +1 -0
- package/dist/Components/MultisigSignerOptions.d.ts +2 -0
- package/dist/Components/MultisigSignerOptions.d.ts.map +1 -0
- package/dist/Components/PrimaryConnectOptions.d.ts +2 -0
- package/dist/Components/PrimaryConnectOptions.d.ts.map +1 -0
- package/dist/Components/SafeInputForm.d.ts +2 -0
- package/dist/Components/SafeInputForm.d.ts.map +1 -0
- package/dist/Components/SafeSelection.d.ts +2 -0
- package/dist/Components/SafeSelection.d.ts.map +1 -0
- package/dist/GraphAuthKit.context-DBwb2jco.js +936 -0
- package/dist/GraphAuthKit.context.d.ts +80 -0
- package/dist/GraphAuthKit.context.d.ts.map +1 -0
- package/dist/GraphAuthKitInner.context.d.ts +109 -0
- package/dist/GraphAuthKitInner.context.d.ts.map +1 -0
- package/dist/client.d.ts +8612 -0
- package/dist/client.d.ts.map +1 -0
- package/dist/constants.d.ts +329 -0
- package/dist/constants.d.ts.map +1 -0
- package/dist/errors.d.ts +21 -0
- package/dist/errors.d.ts.map +1 -0
- package/dist/hooks.d.ts +74 -0
- package/dist/hooks.d.ts.map +1 -0
- package/dist/index.d.ts +8 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +442 -0
- package/dist/safe/SafeEthersSigner.d.ts +37 -0
- package/dist/safe/SafeEthersSigner.d.ts.map +1 -0
- package/dist/safe/SafeMinimal.abi.d.ts +80 -0
- package/dist/safe/SafeMinimal.abi.d.ts.map +1 -0
- package/dist/safe/constants.d.ts +26 -0
- package/dist/safe/constants.d.ts.map +1 -0
- package/dist/safe/index.d.ts +3 -0
- package/dist/safe/index.d.ts.map +1 -0
- package/dist/safe/index.js +11 -0
- package/dist/safe/safeViemActions.d.ts +4 -0
- package/dist/safe/safeViemActions.d.ts.map +1 -0
- package/dist/safe/utils.d.ts +38 -0
- package/dist/safe/utils.d.ts.map +1 -0
- package/dist/safe/utils.test.d.ts +2 -0
- package/dist/safe/utils.test.d.ts.map +1 -0
- package/dist/test-harness/MockGraphAuthKit.context.d.ts +102 -0
- package/dist/test-harness/MockGraphAuthKit.context.d.ts.map +1 -0
- package/dist/test-harness/index.d.ts +2 -0
- package/dist/test-harness/index.d.ts.map +1 -0
- package/dist/test-harness/index.js +63 -0
- package/dist/types.d.ts +54 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/utils-KuRu9vB-.js +218 -0
- package/dist/utils.d.ts +18 -0
- package/dist/utils.d.ts.map +1 -0
- package/dist/utils.test.d.ts +2 -0
- package/dist/utils.test.d.ts.map +1 -0
- package/package.json +93 -0
package/README.md
ADDED
|
@@ -0,0 +1,238 @@
|
|
|
1
|
+
# @edgeandnode/graph-auth-kit
|
|
2
|
+
|
|
3
|
+
Authentication Kit for connecting The Graph apps/dapps to a wallet.
|
|
4
|
+
|
|
5
|
+
Relies on/requires [`wagmi`](https://wagmi.sh/) + [`viem`](https://viem.sh/) for allowing users to connect their wallets and interact with the connected auth state context.
|
|
6
|
+
|
|
7
|
+
Exposes a simple `useGraphAuthKit` hook that lets the app open the connect modal, letting users connect to their wallet of choice (one of: injected/MetaMask, coinbase, WalletConnect, Safe). See integration example below.
|
|
8
|
+
|
|
9
|
+
## Install
|
|
10
|
+
|
|
11
|
+
Currently, `graph-auth-kit` has a lot of peer deps needed to interact with the library. But this may change after testing. At the very least, `wagmi, viem, @tanstack/react-query` will be needed.
|
|
12
|
+
|
|
13
|
+
```bash
|
|
14
|
+
# with bun
|
|
15
|
+
bun add @edgeandnode/graph-auth-kit \
|
|
16
|
+
@edgeandnode/common \
|
|
17
|
+
@edgeandnode/gds \
|
|
18
|
+
@edgeandnode/go \
|
|
19
|
+
@emotion/react \
|
|
20
|
+
@safe-global/api-kit \
|
|
21
|
+
@safe-global/protocol-kit \
|
|
22
|
+
@safe-global/safe-core-sdk-types \
|
|
23
|
+
@tanstack/react-query \
|
|
24
|
+
cookies-next \
|
|
25
|
+
ethers@5.7.2 \
|
|
26
|
+
theme-ui \
|
|
27
|
+
viem@2.x \
|
|
28
|
+
wagmi
|
|
29
|
+
|
|
30
|
+
# with pnpm
|
|
31
|
+
pnpm add @edgeandnode/graph-auth-kit \
|
|
32
|
+
@edgeandnode/common \
|
|
33
|
+
@edgeandnode/gds \
|
|
34
|
+
@edgeandnode/go \
|
|
35
|
+
@emotion/react \
|
|
36
|
+
@safe-global/api-kit \
|
|
37
|
+
@safe-global/protocol-kit \
|
|
38
|
+
@safe-global/safe-core-sdk-types \
|
|
39
|
+
@tanstack/react-query \
|
|
40
|
+
cookies-next \
|
|
41
|
+
ethers@5.7.2 \
|
|
42
|
+
theme-ui \
|
|
43
|
+
viem@2.x \
|
|
44
|
+
wagmi
|
|
45
|
+
```
|
|
46
|
+
|
|
47
|
+
## Usage
|
|
48
|
+
|
|
49
|
+
Properties:
|
|
50
|
+
|
|
51
|
+
- `queryClient` -> [OPTIONAL]. The `GraphAuthKitProvider` renders a `QueryClientProvider` instance. Pass in an instantiated `QueryClient` to use, otherwise, `GraphAuthKit` will instantiate its own.
|
|
52
|
+
- `initialStateCookie` -> [OPTIONAL] wagmi auth state cookie. passed to the `GraphAuthKitProvider` -> `WagmiProvider`
|
|
53
|
+
- we use the exported `AUTH_STORAGE_KEY` from `@edgeandnode/graph-auth-kit` for our wagmi cookie storage.
|
|
54
|
+
- `infuraKey` -> [REQUIRED]
|
|
55
|
+
- `walletConnectProjectID` -> [REQUIRED]
|
|
56
|
+
- `meta` -> [REQUIRED]. information about the app using the lib
|
|
57
|
+
- `meta.name` -> [REQUIRED]. either `Graph Explorer` or `Subgraph Studio`
|
|
58
|
+
- `meta.url` -> the app URL.
|
|
59
|
+
- defaults to: https://thegraph.com/explorer or https://thegraph.com/studio
|
|
60
|
+
- replace with local, staging, dev/testnet as needed
|
|
61
|
+
- `chains` -> the allowed chains/networks for the given app. default is `ALL`
|
|
62
|
+
- `ALL` allowed to connect to: L2 Mainnet (arbitrum-one), L2 Testnet (arbitrum-sepolia), L1 Mainnet (ethereum), L1 Testnet (sepolia)
|
|
63
|
+
- `MAINNET` -> only allowed to connect to L2 Mainnet and L1 Mainnet
|
|
64
|
+
- `TESTNET` -> only allowed to connect to L2 Testnet and L1 Testnet
|
|
65
|
+
|
|
66
|
+
### Example
|
|
67
|
+
|
|
68
|
+
- Setup the `GraphAuthKitProvider`.
|
|
69
|
+
- **Note** you do not need to add the `ConnectModal` component, the `GraphAuthKitProvider` renders it for us
|
|
70
|
+
- **Note** you do not need to add the `QueryClientProvider` as `GraphAuthKitProvider` instantiates and renders it
|
|
71
|
+
- you can pass a `QueryClient` instance to the `GraphAuthKitProvider`, otherwise, it will instantiate its own
|
|
72
|
+
|
|
73
|
+
```tsx
|
|
74
|
+
// _app.tsx
|
|
75
|
+
|
|
76
|
+
import { QueryClient } from '@tanstack/react-query'
|
|
77
|
+
import { getCookie } from 'cookies-next'
|
|
78
|
+
import { AppProps } from 'next'
|
|
79
|
+
import { useRef } from 'react'
|
|
80
|
+
|
|
81
|
+
import { AnalyticsProvider, GDSProvider } from '@edgeandnode/gds'
|
|
82
|
+
import { AUTH_STORAGE_KEY, GraphAuthKitProvider } from '@edgeandnode/graph-auth-kit'
|
|
83
|
+
|
|
84
|
+
import { FutureNextLink } from '../components/FutureNextLink'
|
|
85
|
+
import { Layout } from '../components/Layout'
|
|
86
|
+
|
|
87
|
+
const infuraKey = process.env.INFURA_KEY!
|
|
88
|
+
const walletConnectProjectID = process.env.WALLETCONNECT_PROJECT_ID!
|
|
89
|
+
|
|
90
|
+
import '@edgeandnode/gds/style.css'
|
|
91
|
+
import '../app.css'
|
|
92
|
+
|
|
93
|
+
export default function App({ Component, router, pageProps }: AppProps) {
|
|
94
|
+
const queryClient = useRef<QueryClient>()
|
|
95
|
+
if (!queryClient.current) {
|
|
96
|
+
queryClient.current = new QueryClient({
|
|
97
|
+
defaultOptions: {
|
|
98
|
+
queries: {
|
|
99
|
+
// With SSR, we usually want to set some default staleTime
|
|
100
|
+
// above 0 to avoid refetching immediately on the client
|
|
101
|
+
staleTime: 60 * 1000,
|
|
102
|
+
},
|
|
103
|
+
},
|
|
104
|
+
})
|
|
105
|
+
}
|
|
106
|
+
const cookies = getCookies()
|
|
107
|
+
const initialStateCookie =
|
|
108
|
+
// The nextjs pages router does not make it trivial to retrieve the cookies (app router does though).
|
|
109
|
+
// But, `getServerSideProps` _can_ be used to retrieve the cookies from the request headers,
|
|
110
|
+
// and then passed down as props, which would be available here as `pageProps.cookies`.
|
|
111
|
+
// Otherwise, can parse the cookies uing `getCookies`.
|
|
112
|
+
pageProps.cookies ||
|
|
113
|
+
Object.entries(cookies)
|
|
114
|
+
.filter(([key]) => key.toLowerCase().startsWith(AUTH_STORAGE_KEY.toLowerCase()))
|
|
115
|
+
.reduce<string>(
|
|
116
|
+
(accum, [key, val], idx) => (val == null ? accum : idx === 0 ? `${key}=${val}` : `${accum}; ${key}=${val}`),
|
|
117
|
+
'',
|
|
118
|
+
)
|
|
119
|
+
|
|
120
|
+
return (
|
|
121
|
+
<GDSProvider clientRouter={router} clientLink={FutureNextLink} useLegacyTheme>
|
|
122
|
+
<AnalyticsProvider
|
|
123
|
+
app="EXPLORER"
|
|
124
|
+
clientRouter={router}
|
|
125
|
+
mixpanel={{
|
|
126
|
+
sdk: mixpanel,
|
|
127
|
+
token: process.env.MIXPANEL_TOKEN ?? null,
|
|
128
|
+
}}
|
|
129
|
+
googleAnalytics={{
|
|
130
|
+
sdk: googleAnalytics,
|
|
131
|
+
measurementId: process.env.GOOGLE_ANALYTICS_MEASUREMENT_ID ?? null,
|
|
132
|
+
}}
|
|
133
|
+
>
|
|
134
|
+
<GraphAuthKitProvider
|
|
135
|
+
queryClient={queryClient.current}
|
|
136
|
+
initialStateCookie={initialStateCookie}
|
|
137
|
+
infuraKey={infuraKey}
|
|
138
|
+
walletConnectProjectID={walletConnectProjectID}
|
|
139
|
+
meta={{
|
|
140
|
+
name: 'Graph Explorer',
|
|
141
|
+
url: 'https://thegraph.com/explorer',
|
|
142
|
+
}}
|
|
143
|
+
chains="MAINNET"
|
|
144
|
+
>
|
|
145
|
+
<Layout>
|
|
146
|
+
<DefaultSeo {...defaultSEO} />
|
|
147
|
+
<Component {...pageProps} />
|
|
148
|
+
</Layout>
|
|
149
|
+
<ReactQueryDevtools initialIsOpen={false} />
|
|
150
|
+
</GraphAuthKitProvider>
|
|
151
|
+
</AnalyticsProvider>
|
|
152
|
+
</GDSProvider>
|
|
153
|
+
)
|
|
154
|
+
}
|
|
155
|
+
```
|
|
156
|
+
|
|
157
|
+
- Usage in a component
|
|
158
|
+
|
|
159
|
+
```tsx
|
|
160
|
+
// components/Layout.tsx
|
|
161
|
+
|
|
162
|
+
import { ReactNode } from 'react'
|
|
163
|
+
import { useAccountEffect, useEnsName } from 'wagmi'
|
|
164
|
+
|
|
165
|
+
import { Layout as GDSLayout, UserProfile } from '@edgeandnode/gds'
|
|
166
|
+
import { GlobalFooter, GlobalHeader, NPSForm } from '@edgeandnode/go'
|
|
167
|
+
import { L1Chain, useGraphAuthKitConnector, useGraphAuthKit, useGraphAuthKitAccount } from '@edgeandnode/graph-auth-kit/hooks'
|
|
168
|
+
|
|
169
|
+
import { NavDropDownMenu } from './NavDropDownMenu'
|
|
170
|
+
|
|
171
|
+
export function Layout({ children }: Readonly<{ children: ReactNode }>) {
|
|
172
|
+
const authkit = useGraphAuthKit()
|
|
173
|
+
const { address } = useGraphAuthKitAccount()
|
|
174
|
+
const { data: ens } = useEnsName({ address, blockTag: 'latest', chainId: L1Chain.id })
|
|
175
|
+
const connector = useGraphAuthKitConnector()
|
|
176
|
+
|
|
177
|
+
const walletConnected = Boolean(address)
|
|
178
|
+
|
|
179
|
+
useAccountEffect({
|
|
180
|
+
onConnect(data) {
|
|
181
|
+
console.log('user connected wallet', {data})
|
|
182
|
+
},
|
|
183
|
+
onDisconnect() {
|
|
184
|
+
console.log('user disconnected wallet')
|
|
185
|
+
},
|
|
186
|
+
})
|
|
187
|
+
|
|
188
|
+
return (
|
|
189
|
+
<GDSLayout
|
|
190
|
+
header={
|
|
191
|
+
<GlobalHeader
|
|
192
|
+
activeProduct="EXPLORER"
|
|
193
|
+
basePath="/explorer"
|
|
194
|
+
showSupportButton={walletConnected}
|
|
195
|
+
rigtContent={(defaultContent) => (
|
|
196
|
+
<>
|
|
197
|
+
{!walletConnected ?
|
|
198
|
+
<GlobalHeader.ConnectButton onClick={() => authkit.openConnectModal()} />
|
|
199
|
+
) : (
|
|
200
|
+
<UserProfile
|
|
201
|
+
ethereumAccount={address}
|
|
202
|
+
graphAccount={...}
|
|
203
|
+
ens={ens}
|
|
204
|
+
profileUrl={`/profile/${address}?view=Overview`}
|
|
205
|
+
profileUrlAs={`/profile/${address}?view=Overview`}
|
|
206
|
+
onConnect={() => authkit.openConnectModal()}
|
|
207
|
+
onDisconnect={() => authkit.disconnect()}
|
|
208
|
+
userDropDownMenu={<NavDropDownMenu />}
|
|
209
|
+
accountTag={connector === 'safe' ? 'multisig' : undefined}
|
|
210
|
+
/>
|
|
211
|
+
)}
|
|
212
|
+
</>
|
|
213
|
+
)}
|
|
214
|
+
/>
|
|
215
|
+
}
|
|
216
|
+
footer={
|
|
217
|
+
<>
|
|
218
|
+
<NPSForm sx={{ mb: Spacing['64px'] }} />
|
|
219
|
+
<GlobalFooter />
|
|
220
|
+
</>
|
|
221
|
+
}
|
|
222
|
+
>
|
|
223
|
+
{children}
|
|
224
|
+
</GDSLayout>
|
|
225
|
+
)
|
|
226
|
+
}
|
|
227
|
+
```
|
|
228
|
+
|
|
229
|
+
## Hooks
|
|
230
|
+
|
|
231
|
+
- `useGraphAuthKitAccount` -> This is an override of the [wagmi useAccount hook](https://wagmi.sh/react/api/hooks/useAccount). The reason is, if the user connects with a multisig, the wagmi context is connected with the user-selected EoA, so all of the wagmi context hooks reference this EoA and not the Safe. This returns the wagmi `UseAccountReturnType` but the `address` and `addresses` values include the entered Safe address. It also adds an `eoa` property that is the connected EoA address.
|
|
232
|
+
- `useGraphAuthKitConnector` -> The user selected wallet/connector option.
|
|
233
|
+
|
|
234
|
+
## References
|
|
235
|
+
|
|
236
|
+
- [`wagmi`](https://wagmi.sh/)
|
|
237
|
+
- [`viem`](https://viem.sh/)
|
|
238
|
+
- [Engineering Plan](https://www.notion.so/edgeandnode/Replace-Wallet-Connection-Library-0e4c5e1e015b428dbb52b1f627b712f0)
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ConnectModal.d.ts","sourceRoot":"","sources":["../../src/Components/ConnectModal.tsx"],"names":[],"mappings":"AAQA,wBAAgB,YAAY,gCAsC3B"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { type ElementType, type ReactNode } from 'react';
|
|
2
|
+
import { type GraphAuthKitConnector } from '../types';
|
|
3
|
+
export type ConnectorOptionProps = {
|
|
4
|
+
connector: GraphAuthKitConnector;
|
|
5
|
+
title: ReactNode;
|
|
6
|
+
selected?: boolean;
|
|
7
|
+
disabled?: boolean;
|
|
8
|
+
description?: ReactNode;
|
|
9
|
+
Image: ElementType;
|
|
10
|
+
onClick(): void;
|
|
11
|
+
};
|
|
12
|
+
export declare function ConnectorOption(props: ConnectorOptionProps): import("react").JSX.Element;
|
|
13
|
+
//# sourceMappingURL=ConnectorOption.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ConnectorOption.d.ts","sourceRoot":"","sources":["../../src/Components/ConnectorOption.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,WAAW,EAAE,KAAK,SAAS,EAAE,MAAM,OAAO,CAAA;AAExD,OAAO,EAAE,KAAK,qBAAqB,EAAE,MAAM,UAAU,CAAA;AAErD,MAAM,MAAM,oBAAoB,GAAG;IACjC,SAAS,EAAE,qBAAqB,CAAA;IAChC,KAAK,EAAE,SAAS,CAAA;IAChB,QAAQ,CAAC,EAAE,OAAO,CAAA;IAClB,QAAQ,CAAC,EAAE,OAAO,CAAA;IAClB,WAAW,CAAC,EAAE,SAAS,CAAA;IACvB,KAAK,EAAE,WAAW,CAAA;IAClB,OAAO,IAAI,IAAI,CAAA;CAChB,CAAA;AACD,wBAAgB,eAAe,CAAC,KAAK,EAAE,oBAAoB,+BAqB1D"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"MultisigSignerOptions.d.ts","sourceRoot":"","sources":["../../src/Components/MultisigSignerOptions.tsx"],"names":[],"mappings":"AA8BA,wBAAgB,qBAAqB,gCAuHpC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"PrimaryConnectOptions.d.ts","sourceRoot":"","sources":["../../src/Components/PrimaryConnectOptions.tsx"],"names":[],"mappings":"AAgCA,wBAAgB,qBAAqB,gCAiDpC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SafeInputForm.d.ts","sourceRoot":"","sources":["../../src/Components/SafeInputForm.tsx"],"names":[],"mappings":"AAyEA,wBAAgB,aAAa,gCA2L5B"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SafeSelection.d.ts","sourceRoot":"","sources":["../../src/Components/SafeSelection.tsx"],"names":[],"mappings":"AAkBA,wBAAgB,aAAa,gCA+F5B"}
|