Skip to content

Commit

Permalink
lucid refactor, small management components refactor, scaffolding for…
Browse files Browse the repository at this point in the history
… utxo selection
  • Loading branch information
Piefayth committed Mar 25, 2024
1 parent 839717c commit 04b7c65
Show file tree
Hide file tree
Showing 21 changed files with 649 additions and 176 deletions.
6 changes: 6 additions & 0 deletions src/App.css
Original file line number Diff line number Diff line change
Expand Up @@ -112,4 +112,10 @@ body {

.copy-widget {
margin-left: 10px;
}

.input-label {
font-size: 12px;
font-weight: bold;
margin-bottom: 2px;
}
2 changes: 2 additions & 0 deletions src/app/store.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import fileReducer from '../features/files/filesSlice'
import tooltipReducer from '../features/tooltip/tooltipSlice'
import contextMenuReducer from '../features/contextMenu/contextMenuSlice'
import managementReducer from '../features/management/managementSlice'
import lucidReducer from '../features/management/lucidSlice'

export const store = configureStore({
reducer: {
Expand All @@ -12,6 +13,7 @@ export const store = configureStore({
tooltip: tooltipReducer,
contextMenu: contextMenuReducer,
management: managementReducer,
lucid: lucidReducer
},
})

Expand Down
91 changes: 91 additions & 0 deletions src/components/LucidProvider.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
import { useEffect, useState, createContext, useContext, useRef } from 'react'
import { useDispatch, useSelector } from 'react-redux'
import { Emulator, Lucid, generateSeedPhrase } from 'lucid-cardano'
import { RootState } from '../app/store'
import { Wallet, addWallet, removeWallet } from '../features/management/managementSlice'

interface LucidContextState {
lucid: Lucid | null
isLucidLoading: boolean
}

const LucidContext = createContext<LucidContextState>({
lucid: null,
isLucidLoading: false,
})

export const LucidProvider = ({ children }: { children: React.ReactNode }) => {
const [lucid, setLucid] = useState<Lucid | null>(null)
const [isLucidLoading, setIsLucidLoading] = useState(false)
const [genesisWalletOrUndefined, setGenesisWallet] = useState<Wallet | undefined>(undefined)
const lucidConfig = useSelector((state: RootState) => state.lucid)
const wallets = useSelector((state: RootState) => state.management.wallets)
const dispatch = useDispatch()

const areSideEffectsSafe = useRef(true) // is this really the best way to prevent duplicate effect invocations?

useEffect(() => {
let genesisWallet = genesisWalletOrUndefined
setIsLucidLoading(true)

const initializeLucid = async () => {
const network = lucidConfig.network === "Emulator" ? "Custom" : lucidConfig.network
if (lucid && lucid.network === network) {
// eventually we need to handle provider changes here
return
}

const lucidInstance = await Lucid.new(undefined, network)

let genesisSeed: string | undefined = undefined
let genesisWalletAddress = ''
if (lucidConfig.network === "Emulator" && wallets.length === 0) {
// need to have SOME wallet to provide the emulator provider
genesisSeed = generateSeedPhrase()
lucidInstance.selectWalletFromSeed(genesisSeed)
genesisWalletAddress = await lucidInstance.wallet.address()
} else if (wallets.length > 0) {
lucidInstance.selectWalletFromSeed(wallets[0].seed)
}

if (lucidConfig.network === "Emulator") {
if (areSideEffectsSafe.current) {
areSideEffectsSafe.current = false
genesisWallet = {
address: genesisWalletAddress,
seed: genesisSeed!!
}

dispatch(addWallet(genesisWallet))
setGenesisWallet(genesisWallet)

lucidInstance.provider = new Emulator([{
address: genesisWallet?.address || '',
assets: {
lovelace: 20000000000n
}
}])

setLucid(lucidInstance)
setIsLucidLoading(false)
} else {
areSideEffectsSafe.current = true
}
}
}

initializeLucid()

return
}, [lucidConfig])

return (
<LucidContext.Provider value={{ lucid, isLucidLoading }}>
{children}
</LucidContext.Provider>
)
}

export function useLucid() {
return useContext(LucidContext)
}
5 changes: 4 additions & 1 deletion src/entrypoint.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,14 @@ import { Provider } from 'react-redux'
import App from './App.tsx'
import './index.css'
import { store } from './app/store'
import { LucidProvider } from './components/LucidProvider.tsx'

ReactDOM.createRoot(document.getElementById('root')!).render(
<React.StrictMode>
<Provider store={store}>
<App />
<LucidProvider>
<App />
</LucidProvider>
</Provider>
</React.StrictMode>,
)
32 changes: 32 additions & 0 deletions src/features/management/lucidSlice.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
import { createSlice, PayloadAction } from '@reduxjs/toolkit'
import { Network } from 'lucid-cardano'


export interface LucidState {
network: Network | "Emulator"
isLoading: boolean
}

const initialState: LucidState = {
network: "Emulator",
isLoading: true
}

const lucidSlice = createSlice({
name: 'lucid',
initialState,
reducers: {
setNetwork(state, action:PayloadAction<Network | "Emulator">) {
state.network = action.payload
},
setIsLucidLoading(state, action: PayloadAction<boolean>) {
state.isLoading = action.payload
}
}
})

export const {
setNetwork,
setIsLucidLoading,
} = lucidSlice.actions
export default lucidSlice.reducer
19 changes: 10 additions & 9 deletions src/features/management/managementSlice.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,8 @@ export interface ContractInput {
script: Script,
name: string,
paramsFileName: string,
address: string,
scriptHash: string
}

export interface DeleteContractInput {
Expand All @@ -19,23 +21,21 @@ export interface DeleteContractInput {
}

type Contract = {
version: number
version: number,
} & ContractInput

interface ManagementState {
selectedTabIndex: number
network: Network | "Emulator"
wallets: Wallet[]
contracts: Contract[],
addContractError: string | undefined
}

const initialState: ManagementState = {
selectedTabIndex: 0,
network: "Emulator",
wallets: [],
contracts: [],
addContractError: undefined
addContractError: undefined,
}

const managementSlice = createSlice({
Expand All @@ -45,12 +45,12 @@ const managementSlice = createSlice({
selectTab(state, action: PayloadAction<number>) {
state.selectedTabIndex = action.payload
},
setNetwork(state, action:PayloadAction<Network | "Emulator">) {
state.network = action.payload
},
addWallet(state, action: PayloadAction<Wallet>) {
state.wallets.push(action.payload)
},
removeWallet(state, action: PayloadAction<string>) {
state.wallets.filter(wallet => wallet.address === action.payload)
},
addContract(state, action: PayloadAction<ContractInput>) {
let version = 0
for (let contract of state.contracts) {
Expand All @@ -66,6 +66,7 @@ const managementSlice = createSlice({
version = contract.version + 1
}
}

state.contracts.unshift({
...action.payload,
version
Expand All @@ -80,14 +81,14 @@ const managementSlice = createSlice({
},
setAddContractError(state, action: PayloadAction<string>) {
state.addContractError = action.payload
}
},
}
})

export const {
selectTab,
setNetwork,
addWallet,
removeWallet,
addContract,
removeContract,
clearAddContractError,
Expand Down
76 changes: 0 additions & 76 deletions src/hooks/useLucid.ts

This file was deleted.

2 changes: 1 addition & 1 deletion src/panels/management/BuildResults.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,7 @@ function BuildResults() {

return (
<div className="build-results-content">
<div className="build-results-heading"><strong>Build Results</strong></div>
<div className="management-section-heading"><strong>Build Results</strong></div>
{ project.buildResults && project.buildResults?.length > 0 ? <></> : <div className="no-last-build-notice"> No last build to display. Click "Test" to compile.</div>}
{
project.buildResults?.map((result, index) => {
Expand Down
2 changes: 1 addition & 1 deletion src/panels/management/ManagementPanel.css
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
height: calc(94vh - 45px); /* 45px is the height of the tabs */
}

.build-results-heading {
.management-section-heading {
font-size: 30px;
padding: 10px;
margin-bottom: 10px;
Expand Down
2 changes: 1 addition & 1 deletion src/panels/management/ManagementPanel.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import { useSelector } from 'react-redux'
import { RootState } from '../../app/store'
import { Contracts } from './contract/Contracts'
import { Wallets } from './wallet/Wallets'
import { Transact } from './Transact'
import { Transact } from './transact/Transact'

function ManagementPanel() {
const management = useSelector((state: RootState) => state.management)
Expand Down
2 changes: 1 addition & 1 deletion src/panels/management/ManagementTopBar.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import '../TopBar.css';
import { RootState } from '../../app/store';

function ManagementTopBar() {
const network = useSelector((state: RootState) => state.management.network)
const network = useSelector((state: RootState) => state.lucid.network)
return (
<div className='top-bar management-top-bar'>
<div className='top-bar-item'><strong>Network</strong>: {network}</div>
Expand Down
25 changes: 0 additions & 25 deletions src/panels/management/Transact.tsx

This file was deleted.

Loading

0 comments on commit 04b7c65

Please sign in to comment.