diff --git a/README.md b/README.md index aa033e367..deb7309c6 100644 --- a/README.md +++ b/README.md @@ -10,6 +10,7 @@ NEAR Wallet Selector makes it easy for users to interact with your dApp by provi - [Nightly](https://www.npmjs.com/package/@near-wallet-selector/nightly) - Injected wallet. - [Meteor Wallet](https://www.npmjs.com/package/@near-wallet-selector/meteor-wallet) - Injected wallet. - [Metamask Snap](https://www.npmjs.com/package/@near-wallet-selector/near-snap) - Injected wallet. +- [OKX Wallet](https://www.npmjs.com/package/@near-wallet-selector/okx-wallet) - Injected wallet. - [Narwallets](https://www.npmjs.com/package/@near-wallet-selector/narwallets) - Injected wallet. - [WELLDONE Wallet](https://www.npmjs.com/package/@near-wallet-selector/welldone-wallet) - Injected wallet. - [Coin98 Wallet](https://www.npmjs.com/package/@near-wallet-selector/coin98-wallet) - Injected wallet. @@ -61,6 +62,7 @@ yarn add \ @near-wallet-selector/math-wallet \ @near-wallet-selector/nightly \ @near-wallet-selector/meteor-wallet \ + @near-wallet-selector/okx-wallet \ @near-wallet-selector/narwallets \ @near-wallet-selector/welldone-wallet \ @near-wallet-selector/near-snap \ @@ -83,6 +85,7 @@ npm install \ @near-wallet-selector/math-wallet \ @near-wallet-selector/nightly \ @near-wallet-selector/meteor-wallet \ + @near-wallet-selector/okx-wallet \ @near-wallet-selector/narwallets \ @near-wallet-selector/welldone-wallet \ @near-wallet-selector/near-snap \ @@ -119,6 +122,7 @@ import { setupNearSnap } from "@near-wallet-selector/near-snap"; import { setupMathWallet } from "@near-wallet-selector/math-wallet"; import { setupNightly } from "@near-wallet-selector/nightly"; import { setupMeteorWallet } from "@near-wallet-selector/meteor-wallet"; +import { setupOkxWallet } from "@near-wallet-selector/okx-wallet"; import { setupNarwallets } from "@near-wallet-selector/narwallets"; import { setupWelldoneWallet } from "@near-wallet-selector/welldone-wallet"; import { setupNearSnap } from "@near-wallet-selector/near-snap"; @@ -143,6 +147,7 @@ const selector = await setupWalletSelector({ setupNightly(), setupMeteorWallet(), setupNearSnap(), + setupOkxWallet(), setupNarwallets(), setupWelldoneWallet(), setupLedger(), diff --git a/examples/angular/project.json b/examples/angular/project.json index 91dc82330..26551ea6e 100644 --- a/examples/angular/project.json +++ b/examples/angular/project.json @@ -103,6 +103,11 @@ "glob": "**/*", "input": "packages/near-mobile-wallet/assets/", "output": "assets/" + }, + { + "glob": "**/*", + "input": "packages/okx-wallet/assets/", + "output": "assets/" } ], "styles": ["examples/angular/src/styles.scss"], diff --git a/examples/angular/src/app/pages/wallet-selector/wallet-selector.component.ts b/examples/angular/src/app/pages/wallet-selector/wallet-selector.component.ts index e224fe5ee..24d161a0f 100644 --- a/examples/angular/src/app/pages/wallet-selector/wallet-selector.component.ts +++ b/examples/angular/src/app/pages/wallet-selector/wallet-selector.component.ts @@ -23,6 +23,7 @@ import { setupRamperWallet } from "@near-wallet-selector/ramper-wallet"; import { setupLedger } from "@near-wallet-selector/ledger"; import { setupNearMobileWallet } from "@near-wallet-selector/near-mobile-wallet"; import { setupMintbaseWallet } from "@near-wallet-selector/mintbase-wallet"; +import { setupOKXWallet } from "@near-wallet-selector/okx-wallet"; import { CONTRACT_ID } from "../../../constants"; declare global { @@ -63,6 +64,7 @@ export class WalletSelectorComponent implements OnInit { setupMathWallet(), setupNightly(), setupMeteorWallet(), + setupOKXWallet(), setupNarwallets(), setupWelldoneWallet(), setupHereWallet(), diff --git a/examples/react/contexts/WalletSelectorContext.tsx b/examples/react/contexts/WalletSelectorContext.tsx index b9afdb78e..e2f550d3a 100644 --- a/examples/react/contexts/WalletSelectorContext.tsx +++ b/examples/react/contexts/WalletSelectorContext.tsx @@ -21,6 +21,7 @@ import { setupXDEFI } from "@near-wallet-selector/xdefi"; import { setupRamperWallet } from "@near-wallet-selector/ramper-wallet"; import { setupNearMobileWallet } from "@near-wallet-selector/near-mobile-wallet"; import { setupMintbaseWallet } from "@near-wallet-selector/mintbase-wallet"; +import { setupOKXWallet } from "@near-wallet-selector/okx-wallet"; import type { ReactNode } from "react"; import React, { @@ -73,6 +74,7 @@ export const WalletSelectorContextProvider: React.FC<{ setupNightly(), setupMeteorWallet(), setupNearSnap(), + setupOKXWallet(), setupNarwallets(), setupWelldoneWallet(), setupHereWallet(), diff --git a/examples/react/project.json b/examples/react/project.json index b5958eca0..9288cdee1 100644 --- a/examples/react/project.json +++ b/examples/react/project.json @@ -96,6 +96,11 @@ "glob": "**/*", "input": "packages/near-mobile-wallet/assets/", "output": "assets/" + }, + { + "glob": "**/*", + "input": "packages/okx-wallet/assets/", + "output": "assets/" } ] }, diff --git a/package.json b/package.json index 1ff708107..d09dc8068 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "near-wallet-selector", - "version": "8.9.8", + "version": "8.9.9", "description": "NEAR Wallet Selector makes it easy for users to interact with your dApp by providing an abstraction over various wallets within the NEAR ecosystem", "keywords": [ "near", @@ -23,7 +23,8 @@ "welldone-wallet", "ramper-wallet", "near-mobile-wallet", - "mintbase-wallet" + "mintbase-wallet", + "okx-wallet" ], "homepage": "https://github.com/near/wallet-selector#README", "bugs": { @@ -64,6 +65,7 @@ "build:ramper-wallet": "nx run-many --target=build --projects=ramper-wallet --configuration=production", "build:near-mobile-wallet": "nx run-many --target=build --projects=near-mobile-wallet --configuration=production", "build:mintbase-wallet": "nx run-many --target=build --projects=mintbase-wallet --configuration=production", + "build:okx-wallet": "nx run-many --target=build --projects=okx-wallet --configuration=production", "examples:vanillajs:generateimportmap": "(cd examples/vanillajs && jspm link index.html -o index.html)", "serve:vanillajs": "yarn examples:vanillajs:generateimportmap && http-server -c-1 examples/vanillajs", "lint": "nx workspace-lint && nx run-many --target=lint --all --parallel", diff --git a/packages/account-export/package.json b/packages/account-export/package.json index 970d6ddf2..f54b382d2 100644 --- a/packages/account-export/package.json +++ b/packages/account-export/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/account-export", - "version": "8.9.8", + "version": "8.9.9", "description": "This is the Export Selector UI package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/bitget-wallet/package.json b/packages/bitget-wallet/package.json index 3627eeab2..469576604 100644 --- a/packages/bitget-wallet/package.json +++ b/packages/bitget-wallet/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/bitget-wallet", - "version": "8.9.8", + "version": "8.9.9", "description": "Bitget wallet package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/coin98-wallet/package.json b/packages/coin98-wallet/package.json index 853e8d2cf..9075e0536 100644 --- a/packages/coin98-wallet/package.json +++ b/packages/coin98-wallet/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/coin98-wallet", - "version": "8.9.8", + "version": "8.9.9", "description": "Coin 98 wallet package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/core/package.json b/packages/core/package.json index f05a04caf..90df65add 100644 --- a/packages/core/package.json +++ b/packages/core/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/core", - "version": "8.9.8", + "version": "8.9.9", "description": "This is the core package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/here-wallet/package.json b/packages/here-wallet/package.json index 7a31053f7..6e3115288 100644 --- a/packages/here-wallet/package.json +++ b/packages/here-wallet/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/here-wallet", - "version": "8.9.8", + "version": "8.9.9", "description": "Here wallet package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/ledger/package.json b/packages/ledger/package.json index 76e24c5eb..ed41683d2 100644 --- a/packages/ledger/package.json +++ b/packages/ledger/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/ledger", - "version": "8.9.8", + "version": "8.9.9", "description": "Ledger package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/math-wallet/package.json b/packages/math-wallet/package.json index b9e66530a..b66583c32 100644 --- a/packages/math-wallet/package.json +++ b/packages/math-wallet/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/math-wallet", - "version": "8.9.8", + "version": "8.9.9", "description": "Math wallet package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/meteor-wallet/package.json b/packages/meteor-wallet/package.json index 12d7465d1..e534169a8 100644 --- a/packages/meteor-wallet/package.json +++ b/packages/meteor-wallet/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/meteor-wallet", - "version": "8.9.8", + "version": "8.9.9", "description": "Meteor wallet package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/mintbase-wallet/package.json b/packages/mintbase-wallet/package.json index fb0e14776..5f10da2ec 100644 --- a/packages/mintbase-wallet/package.json +++ b/packages/mintbase-wallet/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/mintbase-wallet", - "version": "8.9.8", + "version": "8.9.9", "description": "Mintbase wallet package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/modal-ui-js/package.json b/packages/modal-ui-js/package.json index ee148fb55..593fe2696 100644 --- a/packages/modal-ui-js/package.json +++ b/packages/modal-ui-js/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/modal-ui-js", - "version": "8.9.8", + "version": "8.9.9", "description": "Modal UI package for NEAR wallet Selector", "keywords": [ "near", diff --git a/packages/modal-ui/package.json b/packages/modal-ui/package.json index be3e0889f..ea524efc3 100644 --- a/packages/modal-ui/package.json +++ b/packages/modal-ui/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/modal-ui", - "version": "8.9.8", + "version": "8.9.9", "description": "Modal UI package for NEAR wallet Selector", "keywords": [ "near", diff --git a/packages/my-near-wallet/package.json b/packages/my-near-wallet/package.json index da2b8ff2f..9af353820 100644 --- a/packages/my-near-wallet/package.json +++ b/packages/my-near-wallet/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/my-near-wallet", - "version": "8.9.8", + "version": "8.9.9", "description": "My Near Wallet package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/narwallets/package.json b/packages/narwallets/package.json index 384dcd3d6..817ebac24 100644 --- a/packages/narwallets/package.json +++ b/packages/narwallets/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/narwallets", - "version": "8.9.8", + "version": "8.9.9", "description": "This is the Narwallets package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/near-mobile-wallet/package.json b/packages/near-mobile-wallet/package.json index 84eca0b23..985b9baee 100644 --- a/packages/near-mobile-wallet/package.json +++ b/packages/near-mobile-wallet/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/near-mobile-wallet", - "version": "8.9.8", + "version": "8.9.9", "description": "NEAR Mobile wallet package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/near-snap/package.json b/packages/near-snap/package.json index 32926972b..790ac45f7 100644 --- a/packages/near-snap/package.json +++ b/packages/near-snap/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/near-snap", - "version": "8.9.8", + "version": "8.9.9", "description": "Metamask snap to interact with Near dapps.", "keywords": [ "near", diff --git a/packages/nearfi/package.json b/packages/nearfi/package.json index 9ca93a56a..d3dfb925f 100644 --- a/packages/nearfi/package.json +++ b/packages/nearfi/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/nearfi", - "version": "8.9.8", + "version": "8.9.9", "description": "Nearfi package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/neth/package.json b/packages/neth/package.json index 8ac0efb5d..d2d9070c9 100644 --- a/packages/neth/package.json +++ b/packages/neth/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/neth", - "version": "8.9.8", + "version": "8.9.9", "description": "Control NEAR accounts with ETH accounts", "author": "mattlockyer", "keywords": [ diff --git a/packages/nightly/package.json b/packages/nightly/package.json index 87d4d0cdb..8be858325 100644 --- a/packages/nightly/package.json +++ b/packages/nightly/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/nightly", - "version": "8.9.8", + "version": "8.9.9", "description": "Nightly wallet package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/okx-wallet/.babelrc b/packages/okx-wallet/.babelrc new file mode 100644 index 000000000..b63f0528f --- /dev/null +++ b/packages/okx-wallet/.babelrc @@ -0,0 +1,10 @@ +{ + "presets": [ + [ + "@nrwl/js/babel", + { + "useBuiltIns": "usage" + } + ] + ] +} diff --git a/packages/okx-wallet/.eslintrc.json b/packages/okx-wallet/.eslintrc.json new file mode 100644 index 000000000..9d9c0db55 --- /dev/null +++ b/packages/okx-wallet/.eslintrc.json @@ -0,0 +1,18 @@ +{ + "extends": ["../../.eslintrc.json"], + "ignorePatterns": ["!**/*"], + "overrides": [ + { + "files": ["*.ts", "*.tsx", "*.js", "*.jsx"], + "rules": {} + }, + { + "files": ["*.ts", "*.tsx"], + "rules": {} + }, + { + "files": ["*.js", "*.jsx"], + "rules": {} + } + ] +} diff --git a/packages/okx-wallet/README.md b/packages/okx-wallet/README.md new file mode 100644 index 000000000..16b60622d --- /dev/null +++ b/packages/okx-wallet/README.md @@ -0,0 +1,71 @@ +# @near-wallet-selector/okx-wallet + +This is the [OKX Wallet](https://chromewebstore.google.com/detail/%E6%AC%A7%E6%98%93-web3-%E9%92%B1%E5%8C%85/mcohilncbfahbmgdjkbpemcciiolgcge) package for NEAR Wallet Selector. + +## Install OKX Wallet + +- [Chrome](https://chromewebstore.google.com/detail/%E6%AC%A7%E6%98%93-web3-%E9%92%B1%E5%8C%85/mcohilncbfahbmgdjkbpemcciiolgcge) +- [Safari](https://apps.apple.com/us/app/okx-wallet/id6463797825) +- [Edge](https://microsoftedge.microsoft.com/addons/detail/%E6%AC%A7%E6%98%93-web3-%E9%92%B1%E5%8C%85/pbpjkcldjiffchgbbndmhojiacbgflha) + +## Installation and Usage + +The easiest way to use this package is to install it from the NPM registry, this package requires `near-api-js` v1.0.0 or above: + +```bash +# Using Yarn +yarn add near-api-js + +# Using NPM. +npm install near-api-js +``` +```bash +# Using Yarn +yarn add @near-wallet-selector/okx-wallet + +# Using NPM. +npm install @near-wallet-selector/okx-wallet +``` + +Then use it in your dApp: + +```ts +import { setupWalletSelector } from "@near-wallet-selector/core"; +import { setupOKXWallet } from "@near-wallet-selector/okx-wallet"; + +// OKX Wallet for Wallet Selector can be setup without any params or it can take few optional params, see options below. +const okxWallet = setupOKXWallet({ + iconUrl: "https://" // optional +}); + +const selector = await setupWalletSelector({ + network: "mainnet", // OKX Wallet only supports NEAR Mainnet at the moment. + modules: [okxWallet], +}); +``` + +## Options + +- `iconUrl`: (`string?`): Image URL for the icon shown in the modal. This can also be a relative path or base64 encoded image. Defaults is `./assets/okx-wallet.png`. +- `deprecated`: (`boolean?`): Deprecated is optional. Default is `false`. + +## Assets + +Assets such as icons can be found in the `/assets` directory of the package. Below is an example using Webpack: + +```ts +import { setupOKXWallet } from "@near-wallet-selector/okx-wallet"; +import okxIconUrl from "@near-wallet-selector/okx-wallet/assets/okx-wallet.png"; + +const okxWallet = setupOKXWallet({ + iconUrl: okxIconUrl +}); +``` + +## Tip + +OKX Wallet only supports NEAR Mainnet at the moment. + +## License + +This repository is distributed under the terms of both the MIT license and the Apache License (Version 2.0). diff --git a/packages/okx-wallet/assets/okx-wallet.png b/packages/okx-wallet/assets/okx-wallet.png new file mode 100644 index 000000000..7e8ec1a85 Binary files /dev/null and b/packages/okx-wallet/assets/okx-wallet.png differ diff --git a/packages/okx-wallet/jest.config.ts b/packages/okx-wallet/jest.config.ts new file mode 100644 index 000000000..a47a2acf8 --- /dev/null +++ b/packages/okx-wallet/jest.config.ts @@ -0,0 +1,16 @@ +/* eslint-disable */ +export default { + displayName: "okx-wallet", + preset: "../../jest.preset.js", + globals: {}, + transform: { + "^.+\\.[tj]s$": [ + "ts-jest", + { + tsconfig: "/tsconfig.spec.json", + }, + ], + }, + moduleFileExtensions: ["ts", "tsx", "js", "jsx"], + coverageDirectory: "../../coverage/packages/okx-wallet", +}; diff --git a/packages/okx-wallet/package.json b/packages/okx-wallet/package.json new file mode 100644 index 000000000..d6c5937bf --- /dev/null +++ b/packages/okx-wallet/package.json @@ -0,0 +1,27 @@ +{ + "name": "@near-wallet-selector/okx-wallet", + "version": "8.9.9", + "description": "OKX Wallet package for NEAR Wallet Selector.", + "keywords": [ + "near", + "blockchain", + "wallets", + "dapps", + "near-protocol", + "near-blockchain", + "wallet selector", + "injected wallet", + "okx wallet" + ], + "repository": { + "type": "git", + "url": "https://github.com/near/wallet-selector.git" + }, + "bugs": { + "url": "https://github.com/near/wallet-selector/issues" + }, + "homepage": "https://github.com/near/wallet-selector/tree/main/packages/okx-wallet", + "peerDependencies": { + "near-api-js": "^1.0.0 || ^2.0.0" + } +} diff --git a/packages/okx-wallet/project.json b/packages/okx-wallet/project.json new file mode 100644 index 000000000..114c948e5 --- /dev/null +++ b/packages/okx-wallet/project.json @@ -0,0 +1,56 @@ +{ + "name": "okx-wallet", + "$schema": "../../node_modules/nx/schemas/project-schema.json", + "sourceRoot": "packages/okx-wallet/src", + "projectType": "library", + "targets": { + "build": { + "executor": "@nrwl/rollup:rollup", + "outputs": ["{options.outputPath}"], + "options": { + "outputPath": "dist/packages/okx-wallet", + "tsConfig": "packages/okx-wallet/tsconfig.lib.json", + "project": "packages/okx-wallet/package.json", + "entryFile": "packages/okx-wallet/src/index.ts", + "buildableProjectDepsInPackageJsonType": "dependencies", + "compiler": "babel", + "format": ["esm", "cjs"], + "assets": [ + { + "glob": "packages/okx-wallet/README.md", + "input": ".", + "output": "." + }, + { + "glob": "packages/okx-wallet/assets/*", + "input": ".", + "output": "assets" + } + ] + } + }, + "lint": { + "executor": "@nx/linter:eslint", + "outputs": ["{options.outputFile}"], + "options": { + "lintFilePatterns": ["packages/okx-wallet/**/*.ts"] + } + }, + "test": { + "executor": "@nx/jest:jest", + "outputs": ["{workspaceRoot}/coverage/packages/okx-wallet"], + "options": { + "jestConfig": "packages/okx-wallet/jest.config.ts", + "passWithNoTests": true + } + }, + "deploy": { + "executor": "ngx-deploy-npm:deploy", + "options": { + "access": "public" + }, + "dependsOn": ["^deploy"] + } + }, + "tags": ["injected-wallet"] +} diff --git a/packages/okx-wallet/src/index.ts b/packages/okx-wallet/src/index.ts new file mode 100644 index 000000000..73172ebdb --- /dev/null +++ b/packages/okx-wallet/src/index.ts @@ -0,0 +1,2 @@ +export { setupOKXWallet } from "./lib/okx-wallet"; +export type { OKXWalletParams } from "./lib/okx-wallet"; diff --git a/packages/okx-wallet/src/lib/icon.ts b/packages/okx-wallet/src/lib/icon.ts new file mode 100644 index 000000000..5ba8925f5 --- /dev/null +++ b/packages/okx-wallet/src/lib/icon.ts @@ -0,0 +1 @@ +export default `data:image/png;base64,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`; diff --git a/packages/okx-wallet/src/lib/injected-okx-wallet.ts b/packages/okx-wallet/src/lib/injected-okx-wallet.ts new file mode 100644 index 000000000..aa967c5f3 --- /dev/null +++ b/packages/okx-wallet/src/lib/injected-okx-wallet.ts @@ -0,0 +1,73 @@ +export interface AccessKey { + publicKey: string; + secretKey: string; +} + +interface RequestSignInResponse { + accessKey: AccessKey; + accountId: string; + error: string | { type: string }; +} + +export type SignOutResponse = true | { error: string | { type: string } }; + +interface RequestSignInParams { + contractId?: string; + methodNames?: Array; +} + +interface Action { + methodName: string; + args: object; + gas: string; + deposit: string; +} + +interface SignAndSendTransactionParams { + receiverId: string; + actions: Array; +} + +export interface SignAndSendTransactionResponse { + method: string; + txHash: string; + code: number; +} + +interface Transaction { + receiverId: string; + actions: Array; +} + +interface RequestSignTransactionsParams { + transactions: Array; +} + +interface RequestSignTransactionsResponse { + txs: Array<{ + signedTx: string; + }>; +} + +export interface OkxEvents { + signIn: () => void; + signOut: () => void; + accountChanged: (changedAccountId: string) => void; +} + +export interface InjectedOkx { + getAccountId: () => string | null; + requestSignIn: ( + params: RequestSignInParams + ) => Promise; + signOut: () => Promise; + isSignedIn: () => boolean; + on: ( + event: Event, + callback: OkxEvents[Event] + ) => void; + signTransaction: (params: SignAndSendTransactionParams) => Promise; + requestSignTransactions: ( + params: RequestSignTransactionsParams + ) => Promise; +} diff --git a/packages/okx-wallet/src/lib/okx-wallet.spec.ts b/packages/okx-wallet/src/lib/okx-wallet.spec.ts new file mode 100644 index 000000000..56b45c01b --- /dev/null +++ b/packages/okx-wallet/src/lib/okx-wallet.spec.ts @@ -0,0 +1,133 @@ +/* eslint-disable @nx/enforce-module-boundaries */ +import { mock } from "jest-mock-extended"; +import type { ProviderService } from "packages/core/src/lib/services"; +import type { FinalExecutionOutcome } from "near-api-js/lib/providers"; + +import { setupOKXWallet } from "./okx-wallet"; +import { mockWallet } from "../../../core/src/lib/testUtils"; +import type { AccessKey, SignOutResponse } from "./injected-okx-wallet"; +import type { InjectedWallet } from "../../../core/src/lib/wallet"; + +const accountId = "test-account.testnet"; +const transactions = [ + { + signerId: accountId, + receiverId: "test.testnet", + actions: [], + }, +]; + +jest.mock("near-api-js/lib/transaction", () => { + return { + ...jest.requireActual("near-api-js/lib/transaction"), + SignedTransaction: { + ...jest.requireActual("near-api-js/lib/transaction").SignedTransaction, + decode: jest.fn().mockReturnValue({}), + }, + }; +}); + +const mockOkx = () => { + const okxwallet = { + near: { + getAccountId: jest.fn().mockReturnValue(""), + requestSignIn: jest.fn(async () => { + window.okxwallet.near!.getAccountId = jest + .fn() + .mockReturnValue(accountId); + + return { + accountId, + accessKey: mock(), + error: "", + }; + }), + signOut: jest.fn().mockReturnValue(mock()), + isSignedIn: jest.fn().mockReturnValue(true), + on: jest.fn(), + signTransaction: jest.fn().mockResolvedValue("signedTx"), + requestSignTransactions: jest.fn().mockResolvedValue({ + txs: [{ signedTx: "signedTx" }], + }), + }, + }; + + window.okxwallet = okxwallet; + + return window.okxwallet.near; +}; + +const createOKXWallet = async () => { + const injectedOkx = mockOkx(); + const provider = mock(); + provider.sendTransaction.mockResolvedValue(mock()); + const { wallet } = await mockWallet(setupOKXWallet(), { + provider, + }); + + return { + wallet, + injectedOkx, + }; +}; + +afterEach(() => { + jest.resetModules(); +}); + +describe("signIn", () => { + it("sign into okx wallet", async () => { + const { wallet, injectedOkx } = await createOKXWallet(); + const accounts = await wallet.signIn({ contractId: "test.testnet" }); + expect(injectedOkx!.requestSignIn).toHaveBeenCalled(); + expect(accounts[0]?.accountId).toBe(accountId); + }); +}); + +describe("signOut", () => { + it("sign out of okx wallet", async () => { + const { wallet, injectedOkx } = await createOKXWallet(); + await wallet.signIn({ contractId: "test.testnet" }); + await wallet.signOut(); + + expect(injectedOkx!.signOut).toHaveBeenCalled(); + }); +}); + +describe("getAccounts", () => { + it("returns accounts", async () => { + const { wallet, injectedOkx } = await createOKXWallet(); + await wallet.signIn({ contractId: "test.testnet" }); + const result = await wallet.getAccounts(); + + expect(injectedOkx!.getAccountId).toHaveBeenCalled(); + expect(result).toEqual([{ accountId, publicKey: undefined }]); + }); +}); + +describe("signTransaction", () => { + it("sign transaction in okx wallet", async () => { + const { wallet, injectedOkx } = await createOKXWallet(); + await wallet.signIn({ contractId: "test.testnet" }); + await wallet.signAndSendTransaction({ + signerId: accountId, + receiverId: "test.testnet", + actions: [], + }); + + expect(injectedOkx!.signTransaction).toHaveBeenCalled(); + }); +}); + +describe("signAndSendTransactions", () => { + it("sign transactions in okx wallet", async () => { + const { wallet, injectedOkx } = await createOKXWallet(); + await wallet.signIn({ contractId: "test.testnet" }); + const result = await wallet.signAndSendTransactions({ + transactions, + }); + + expect(injectedOkx!.requestSignTransactions).toHaveBeenCalled(); + expect(result.length).toEqual(transactions.length); + }); +}); diff --git a/packages/okx-wallet/src/lib/okx-wallet.ts b/packages/okx-wallet/src/lib/okx-wallet.ts new file mode 100644 index 000000000..05b4b5768 --- /dev/null +++ b/packages/okx-wallet/src/lib/okx-wallet.ts @@ -0,0 +1,247 @@ +import { isMobile } from "is-mobile"; +import { SignedTransaction } from "near-api-js/lib/transaction"; +import { isCurrentBrowserSupported, waitFor } from "@near-wallet-selector/core"; + +import type { + Action, + Optional, + Transaction, + InjectedWallet, + FunctionCallAction, + WalletModuleFactory, + WalletBehaviourFactory, +} from "@near-wallet-selector/core"; + +import icon from "./icon"; +import type { InjectedOkx } from "./injected-okx-wallet"; + +let downloadUrl = + "https://chromewebstore.google.com/detail/%E6%AC%A7%E6%98%93-web3-%E9%92%B1%E5%8C%85/mcohilncbfahbmgdjkbpemcciiolgcge"; + +if (isCurrentBrowserSupported(["safari"])) { + downloadUrl = "https://apps.apple.com/us/app/okx-wallet/id6463797825"; +} + +if (isCurrentBrowserSupported(["edge-chromium"])) { + downloadUrl = + "https://microsoftedge.microsoft.com/addons/detail/%E6%AC%A7%E6%98%93-web3-%E9%92%B1%E5%8C%85/pbpjkcldjiffchgbbndmhojiacbgflha"; +} + +declare global { + interface Window { + okxwallet: { + near: InjectedOkx | undefined; + }; + } +} + +export interface OKXWalletParams { + iconUrl?: string; + deprecated?: boolean; +} + +interface OkxState { + wallet: InjectedOkx; +} + +const isInstalled = () => { + return waitFor(() => !!window.okxwallet?.near).catch(() => false); +}; + +const setupOkxState = (): OkxState => { + const wallet = window.okxwallet?.near!; + return { + wallet, + }; +}; + +const OKXWallet: WalletBehaviourFactory = async ({ + metadata, + store, + emitter, + logger, + id, + provider, +}) => { + const _state = setupOkxState(); + + const signOut = async () => { + if (!_state.wallet.isSignedIn()) { + return; + } + + await _state.wallet.signOut(); + }; + + const setupEvents = () => { + _state.wallet.on("accountChanged", async (newAccountId) => { + logger.log("onAccountChange", newAccountId); + emitter.emit("signedOut", null); + }); + }; + + const isValidActions = ( + actions: Array + ): actions is Array => { + return actions.every((x) => x.type === "FunctionCall"); + }; + + const transformActions = (actions: Array) => { + const validActions = isValidActions(actions); + + if (!validActions) { + throw new Error( + `Only 'FunctionCall' actions types are supported by ${metadata.name}` + ); + } + + return actions.map((x) => x.params); + }; + + const transformTransactions = ( + transactions: Array> + ) => { + return transactions.map((transaction) => { + return { + receiverId: transaction.receiverId, + actions: transformActions(transaction.actions), + }; + }); + }; + + if (_state.wallet && _state.wallet.isSignedIn()) { + setupEvents(); + } + + const getAccounts = async () => { + const { selectedWalletId } = store.getState(); + if (selectedWalletId === id) { + await waitFor(() => !!_state.wallet?.isSignedIn(), { + timeout: 1000, + }).catch(); + } + + const accountId = _state.wallet.getAccountId(); + + if (!accountId) { + return []; + } + + return [{ accountId }]; + }; + + const getSignedTransaction = (signedTx: string) => { + const buf = Buffer.from(signedTx, "base64"); + const signedTransaction = SignedTransaction.decode(buf); + return signedTransaction; + }; + + return { + async signIn({ contractId, methodNames }) { + try { + const { accessKey, accountId } = await _state.wallet.requestSignIn({ + contractId, + methodNames, + }); + setupEvents(); + + const publicKey = accessKey?.publicKey; + + return [ + { + accountId, + publicKey: publicKey ? publicKey.toString() : undefined, + }, + ]; + } catch (_) { + await signOut(); + throw new Error("Failed to sign in"); + } + }, + + signOut, + + getAccounts, + + async verifyOwner() { + throw new Error(`Method not supported by ${metadata.name}`); + }, + + async signMessage() { + throw new Error(`Method not supported by ${metadata.name}`); + }, + + async signAndSendTransaction({ signerId, receiverId, actions }) { + logger.log("signAndSendTransaction", { signerId, receiverId, actions }); + + const { contract } = store.getState(); + + if (!_state.wallet.isSignedIn() || !contract) { + throw new Error("Wallet not signed in"); + } + + try { + const signedTx = await _state.wallet.signTransaction({ + receiverId: receiverId || contract.contractId, + actions: transformActions(actions), + }); + const signedTransaction = getSignedTransaction(signedTx); + return provider.sendTransaction(signedTransaction); + } catch (error) { + throw new Error("sign Error"); + } + }, + + async signAndSendTransactions({ transactions }) { + logger.log("signAndSendTransactions", { transactions }); + + if (!_state.wallet.isSignedIn()) { + throw new Error("Wallet not signed in"); + } + + try { + const resp = await _state.wallet.requestSignTransactions({ + transactions: transformTransactions(transactions), + }); + + const { txs } = resp; + const results = []; + for (let i = 0; i < txs.length; i++) { + const signedTransaction = getSignedTransaction(txs[i].signedTx); + results.push(await provider.sendTransaction(signedTransaction)); + } + return results; + } catch (error) { + throw new Error("sign Error"); + } + }, + }; +}; + +export function setupOKXWallet({ + iconUrl = icon, + deprecated = false, +}: OKXWalletParams = {}): WalletModuleFactory { + return async () => { + const mobile = isMobile(); + if (mobile) { + return null; + } + + const installed = await isInstalled(); + + return { + id: "okx-wallet", + type: "injected", + metadata: { + name: "OKX Wallet", + description: "Browser extension wallet", + iconUrl, + downloadUrl, + deprecated, + available: installed, + }, + init: OKXWallet, + }; + }; +} diff --git a/packages/okx-wallet/tsconfig.json b/packages/okx-wallet/tsconfig.json new file mode 100644 index 000000000..3aaed7519 --- /dev/null +++ b/packages/okx-wallet/tsconfig.json @@ -0,0 +1,20 @@ +{ + "extends": "../../tsconfig.base.json", + "compilerOptions": { + "forceConsistentCasingInFileNames": true, + "strict": true, + "noImplicitReturns": true, + "noFallthroughCasesInSwitch": true, + "resolveJsonModule": true + }, + "files": [], + "include": [], + "references": [ + { + "path": "./tsconfig.lib.json" + }, + { + "path": "./tsconfig.spec.json" + } + ] +} diff --git a/packages/okx-wallet/tsconfig.lib.json b/packages/okx-wallet/tsconfig.lib.json new file mode 100644 index 000000000..e85ef50f6 --- /dev/null +++ b/packages/okx-wallet/tsconfig.lib.json @@ -0,0 +1,10 @@ +{ + "extends": "./tsconfig.json", + "compilerOptions": { + "outDir": "../../dist/out-tsc", + "declaration": true, + "types": [] + }, + "include": ["**/*.ts"], + "exclude": ["jest.config.ts", "**/*.spec.ts", "**/*.test.ts"] +} diff --git a/packages/okx-wallet/tsconfig.spec.json b/packages/okx-wallet/tsconfig.spec.json new file mode 100644 index 000000000..b506d384e --- /dev/null +++ b/packages/okx-wallet/tsconfig.spec.json @@ -0,0 +1,9 @@ +{ + "extends": "./tsconfig.json", + "compilerOptions": { + "outDir": "../../dist/out-tsc", + "module": "commonjs", + "types": ["jest", "node"] + }, + "include": ["jest.config.ts", "**/*.spec.ts"] +} diff --git a/packages/ramper-wallet/package.json b/packages/ramper-wallet/package.json index 30e5620ce..ae25e6c8a 100644 --- a/packages/ramper-wallet/package.json +++ b/packages/ramper-wallet/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/ramper-wallet", - "version": "8.9.8", + "version": "8.9.9", "description": "Ramper wallet package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/sender/package.json b/packages/sender/package.json index 5a857637e..f1d31cc54 100644 --- a/packages/sender/package.json +++ b/packages/sender/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/sender", - "version": "8.9.8", + "version": "8.9.9", "description": "Sender wallet package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/wallet-connect/package.json b/packages/wallet-connect/package.json index 027830542..8fe1e44c5 100644 --- a/packages/wallet-connect/package.json +++ b/packages/wallet-connect/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/wallet-connect", - "version": "8.9.8", + "version": "8.9.9", "description": "Wallet Connect package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/wallet-utils/package.json b/packages/wallet-utils/package.json index 0831d6c6e..6f4498822 100644 --- a/packages/wallet-utils/package.json +++ b/packages/wallet-utils/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/wallet-utils", - "version": "8.9.8", + "version": "8.9.9", "description": "Wallet utils package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/welldone-wallet/package.json b/packages/welldone-wallet/package.json index ca0752717..588f2b793 100644 --- a/packages/welldone-wallet/package.json +++ b/packages/welldone-wallet/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/welldone-wallet", - "version": "8.9.8", + "version": "8.9.9", "description": "Welldone wallet package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/packages/xdefi/package.json b/packages/xdefi/package.json index ccaba40b8..cbdf38855 100644 --- a/packages/xdefi/package.json +++ b/packages/xdefi/package.json @@ -1,6 +1,6 @@ { "name": "@near-wallet-selector/xdefi", - "version": "8.9.8", + "version": "8.9.9", "description": "This is the XDEFI package for NEAR Wallet Selector.", "keywords": [ "near", diff --git a/tsconfig.base.json b/tsconfig.base.json index 8dfb318b0..52eaeebdd 100644 --- a/tsconfig.base.json +++ b/tsconfig.base.json @@ -92,6 +92,9 @@ "@near-wallet-selector/mintbase-wallet": [ "packages/mintbase-wallet/src/index.ts" ], + "@near-wallet-selector/okx-wallet": [ + "packages/okx-wallet/src/index.ts" + ], "crypto": [ "node_modules/crypto-browserify" ],