-
Notifications
You must be signed in to change notification settings - Fork 66
Home
Our SubWallet is forked from polkadot-js/extension. We aim to add more features while still maintaining our ability to rebase the polkadot origin at any time.
The extension is compiled from folder packages/extension-koni
-
Background environment:
- Compiled from
packages/extension-koni/src/background.ts
.
- Used to handle messages from Extensions pages and Chrome tabs via Chrome API Message Passing.
- Saves all states to store and persist in Chrome local storage.
- Runs cronjobs.
- Compiled from
-
Extension:
- Frontend and page of extension.
- popup.html: Frontend page opens when users click on extension icon in browser.
- portfolio.html: Frontend displays more complicated view.
-
Inject Scripts:
- Inject scripts into Chrome tabs.
All data requests must be called and processed in the background. Extension Pages and Inject Scripts use data from the background environment and do not call APIs directly.
- extension-base - Contains main features running in background, calls API, persists data in Chrome local storage and injects scripts.
- extension-dapp - Convenient wrapper that simplifies data extraction for any DApp wishing to integrate the extension (or any extension that supports the interface).
- extension-inject - Convenient wrapper that allows extension developers to inject their extension for use by any DApp.
- extension-chains - Definitions for chains that are supported by this extension, containing the bare definitions as well as a stripped-down (call-only) metadata format.
- extension-dapp - Actual in-depth technical breakdown is given in the next section for any DApp developer wishing to work with raw objects injected into window. However, convenient wrappers are provided to allow any DApp to use this extension (or any other extension that conforms to the interface) without having to manage any additional info.
- extension-mocks - Mock data for testing.
- extension-compat-metamask - Compatible with Metamask.
- extension-koni-base - Custom package, extension base
- extension-koni-ui (replace extension-ui) - UI components for the extension to build up the pop-up.
- extension-koni (replace extension) - All injection and background processing logic (main entry).
- API is defined in folder
packages/extension-koni-base/src/api
- Add new files depending on types of API
- Simple API can be defined in Function, more complicated API should be defined in Object.
Store is used to persist data into local storage. Store is defined in folder packages/extension-koni-base/src/store
- Store class should extend class
BaseStore
orSubscribableStore
and overwrite class prefix call via constructor.-
BaseStore
includes basic functions that are persisted in Chrome local storage. -
SubscribableStore
extendsBaseStore
, includes rxjs subject and can be subscribed with methodgetSubject()
. This subject is triggered every time data is set.
export default class PriceStore extends SubscribableStore<PriceJson> { constructor () { super(EXTENSION_PREFIX ? `${EXTENSION_PREFIX}price` : null); } }
-
- Defined in class
KoniState
and called byKoniExtension
,KoniTabs
orKoniCron
.export default class KoniState extends State { private readonly priceStore = new PriceStore(); private priceStoreReady = false; public setPrice (priceData: PriceJson, callback?: (priceData: PriceJson) => void): void { ... } public getPrice (update: (value: PriceJson) => void): void { ... } public subscribePrice () { return this.priceStore.getSubject(); } }
Subwallet extension uses message passing concept via browser API to interact between Background - Extension - Chrome Tabs.
- Extension or Chrome Tabs send a message with ID and type to Background.
- Background handles message by ID, type and response data.
- There are 2 message types:
- One time message: Extension or Chrome Tabs will send message request and listen to response. Listener will be deleted after response has been received.
- Subscription message: Same as one time message but listener continues to receive data util window is closed.
- Steps to add new message handle:
- Add request type:
- New request type must be defined in interface
KoniRequestSignatures
export interface KoniRequestSignatures { 'pri(price.getPrice)': [RequestPrice, PriceJson] // Message type from extension 'pri(price.getSubscription)': [RequestSubscribePrice, boolean, PriceJson] // Message type from extension with subscription 'pub(utils.getRandom)': [RandomTestRequest, number] // Message type from Tabs }
- Every message type must includ:
- Type name like
pri(price.getPrice)
. Message type from extension must start withpri
, message type from Tabs must start withpub
. - Request type like
RequestPrice
- Response type like
PriceJson
- Subscription param type (optional) like
PriceJson
- Type name like
- New request type must be defined in interface
- Add handle (Background):
- Add new case in function handle of
KoniExtension
orKoniTabs
of packageextension-koni-base
- Add new case in function handle of
- Add caller (Extension, Chrome Tabs):
- Add new function in file
messaging.ts
of packageextension-koni-ui
to send request and handle received data.
- Add new function in file
- Add request type:
Cronjob is defined in folder packages/extension-koni-base/src/cron
.
- Group of cron actions should be defined in a separate file in this folder.
- Defining new cronjob in method init of class
KoniCron
- SubWallet extension UI is built with ReactJS.
- Popup: Main extension page shows up when users click on extension icon in browser extension list.
- Portfolio (Coming soon): Display more complicated view like dashboard, transaction, etc...
- Other folders:
- assets: images, resources of extensions
- components: common components used in extension pages
- hooks: public hook for global function
- i18n: internationalization
- stores: redux stores generate with react hook
- partials: header components
- util: utilities methods
- messaging.ts: send to background and handle return message.
- Subwallet extension uses redux-tookit to generate store.
- Define redux store reducers and states in a separate file by method
createSlice
in redux toolkit. - Map reducer into root store in file index.ts.
Read "Add message handle"
Extension auto validates code with eslint. Please set up eslint in editor and run yarn lint
before committing code.
SubWallet runs test with jest. Create new file with name filename.spec.ts
to write test.
- Please run
yarn lint
andyarn test
. - Versioning:
- Dev version: Dev version is auto generated by Github Action.
- Stable version:
- Manual change version in main file package.json from x.y.z-nn to x.y.z
- Update CHANGELOG.md
- Github Action will auto generate version file of each package.