add authorization check and step progress

This commit is contained in:
Barry Gitarts 2019-08-29 11:43:22 -04:00 committed by Barry G
parent 1e8f391f61
commit dcb329557f
5 changed files with 63 additions and 15 deletions

View File

@ -1,4 +1,4 @@
import React, { useContext, useMemo, useEffect } from 'react'
import React, { useContext, useState, useMemo, useEffect } from 'react'
import { Formik } from 'formik'
import { makeStyles } from '@material-ui/core/styles'
import classnames from 'classnames'
@ -27,6 +27,10 @@ import FundStepper from './FundStepper'
const { addGiverAndDonate } = LiquidPledging.methods
const NOT_SUBMITTED = 'Not Submitted'
const SUBMITTED = 'Submitted'
const CONFIRMED = 'Confirmed'
const useStyles = makeStyles(styles)
const getProjectId = response => {
const { events: { ProjectAdded: { returnValues: { idProject } } } } = response
@ -36,6 +40,20 @@ const addProjectSucessMsg = response => {
const { events: { ProjectAdded: { returnValues: { idProject } } } } = response
return `Project created with ID of ${idProject}, will redirect to your new project page in a few seconds`
}
const STEPS = ['Connect', 'Authorize Amount', 'Fund', 'Confirmation']
function stepperProgress(values, projectData, submissionState) {
console.log({values, projectData})
if (submissionState === CONFIRMED) return 4
if (submissionState === SUBMITTED) return 3
if (!projectData.account) return 0
const { manifest: { goalToken }, authorization } = projectData
const { amount } = values
const { chainReadibleFn } = getTokenByAddress(goalToken)
const weiAmount = amount ? chainReadibleFn(amount) : '0'
const isAuthorized = toBN(authorization).gte(toBN(weiAmount))
if (!isAuthorized) return 1
return 2
}
const optimisticUpdate = (client, pledgesInfo, weiAmount) => {
const { __typename } = pledgesInfo
const updatedLifetimeReceived = toBN(weiAmount).add(toBN(pledgesInfo.lifetimeReceived)).toString()
@ -51,6 +69,7 @@ const optimisticUpdate = (client, pledgesInfo, weiAmount) => {
}
const SubmissionSection = ({ classes, projectData, projectId, profileData, startPolling, client }) => {
const { account, enableEthereum, openSnackBar, prices } = useContext(FundingContext)
const [submissionState, setSubmissionState] = useState(NOT_SUBMITTED)
const { projectAge, projectAssets, manifest } = projectData
const { pledgesInfos, projectInfo } = profileData
const pledgesInfo = pledgesInfos[0]
@ -80,11 +99,13 @@ const SubmissionSection = ({ classes, projectData, projectId, profileData, start
.send({gas: estimatedGas + 100})
.on('transactionHash', (hash) => {
optimisticUpdate(client, pledgesInfo, weiAmount)
setSubmissionState(SUBMITTED)
openSnackBar('success', `Submitted funding request to chain. TX Hash: ${hash}`)
})
.then(async res => {
console.log({res})
startPolling(10000)
setSubmissionState(CONFIRMED)
openSnackBar('success', 'Funding Confirmed')
})
.catch(e => {
@ -110,6 +131,7 @@ const SubmissionSection = ({ classes, projectData, projectId, profileData, start
}) => {
const { firstHalf, secondHalf, fullWidth } = classes
const usdValue = manifest ? convertTokenAmountUsd(manifest.goalToken, values.amount, prices) : 0
const activeStep = stepperProgress(values, projectData, submissionState)
return (
<form onSubmit={handleSubmit} className={classes.submissionRoot}>
@ -182,7 +204,7 @@ const SubmissionSection = ({ classes, projectData, projectId, profileData, start
<div className={classes.amountText}>{getTokenLabel(manifest.goalToken)}</div>
</div>
<Button type="submit" color="primary" variant="contained" className={classnames(classes.formButton)}>{isSubmitting ? 'Ethereum Submission In Progress' : buttonText}</Button>
<FundStepper />
<FundStepper steps={STEPS} activeStep={activeStep} />
</div>}
</form>
)

View File

@ -145,15 +145,8 @@ const useStyles = makeStyles(theme => ({
},
}));
function getSteps() {
return ['Connect', 'Authorize Amount', 'Fund', 'Confirmation'];
}
export default function CustomizedSteppers() {
export default function CustomizedSteppers({ activeStep, steps }) {
const classes = useStyles();
const [activeStep, setActiveStep] = React.useState(1);
console.log({setActiveStep})
const steps = getSteps();
return (
<div className={classes.root}>

View File

@ -2,6 +2,7 @@ import { useState, useEffect, useMemo, useContext } from 'react'
import { unnest } from 'ramda'
import { timeSinceBlock } from '../../utils/dates'
import { getFiles, getFilesWeb, ipfs, getFilesWebTheGraph } from '../../utils/ipfs'
import { getAllowanceFromAddress } from '../../utils/currencies'
import { arrayToObject } from '../../utils/array'
import { FundingContext } from '../../context'
import { getDelegateProfiles } from '../../actions/profiles'
@ -110,12 +111,20 @@ const getProjectManifest = (data, assets) => {
}
}
async function getAuthorization(data, setState) {
if (!data.profile) return
const { profile: { projectInfo: { goalToken } } } = data
const allowance = await getAllowanceFromAddress(goalToken)
setState(allowance)
}
export function useProjectData(projectId, data) {
const [projectAge, setAge] = useState(null)
const [creator, setCreator] = useState(null)
const [projectAssets, setAssets] = useState(null)
const [ipfsReady, setIpfsState] = useState(null)
const [delegateProfiles, setDelegateProfiles] = useState(null)
const [authorization, setAuthorization] = useState(0)
const { account, openSnackBar, syncWithRemote } = useContext(FundingContext)
useEffect(() => {
@ -138,10 +147,15 @@ export function useProjectData(projectId, data) {
getProjectAssets(data, setAssets)
}, [ipfsReady, data])
useEffect(() => {
if (account) getAuthorization(data, setAuthorization)
}, [account, data])
const manifest = useMemo(() => getProjectManifest(data, projectAssets), [data, projectAssets, projectId])
return {
account,
authorization,
creator,
projectAge,
projectAssets,

View File

@ -70,7 +70,7 @@ class App extends React.Component {
enableEthereum = async () => {
try {
await await window.ethereum.enable()
await window.ethereum.enable()
const account = await web3.eth.getCoinbase()
this.setState({ account })
this.web3Init()

View File

@ -1,8 +1,10 @@
/*global web3*/
import { memoizeWith, identity } from 'ramda'
import SNT from '../embarkArtifacts/contracts/SNT'
import DAI from '../embarkArtifacts/contracts/DAI'
import cDAI from '../embarkArtifacts/contracts/cDAI'
import cETH from '../embarkArtifacts/contracts/cETH'
import LiquidPledging from '../embarkArtifacts/contracts/LiquidPledging'
import { toEther, toWei, compoundWhole, compoundToChain } from './conversions'
export const TOKEN_ICON_API = 'https://raw.githubusercontent.com/TrustWallet/tokens/master/images'
@ -16,7 +18,8 @@ export const currencies = [
width: '2rem',
contract: SNT,
humanReadibleFn: toEther,
chainReadibleFn: toWei
chainReadibleFn: toWei,
getAllowance: () => getLpAllowance(SNT)
},
{
value: '0xf5dce57282a584d2746faf1593d3121fcac444dc',
@ -25,7 +28,8 @@ export const currencies = [
width: '2rem',
contract: cDAI,
humanReadibleFn: compoundWhole,
chainReadibleFn: compoundToChain
chainReadibleFn: compoundToChain,
getAllowance: () => getLpAllowance(cDAI)
},
{
value: '0x4Ddc2D193948926D02f9B1fE9e1daa0718270ED5',
@ -34,7 +38,8 @@ export const currencies = [
width: '2rem',
contract: cETH,
humanReadibleFn: compoundWhole,
chainReadibleFn: compoundToChain
chainReadibleFn: compoundToChain,
getAllowance: () => getLpAllowance(cETH)
},
{
value: '0xc02aaa39b223fe8d0a0e5c4f27ead9083c756cc2',
@ -51,7 +56,8 @@ export const currencies = [
width: '2rem',
contract: DAI,
humanReadibleFn: toEther,
chainReadibleFn: toWei
chainReadibleFn: toWei,
getAllowance: () => getLpAllowance(DAI)
}
]
@ -71,3 +77,16 @@ export const getFormattedPledgeAmount = pledge => {
const { humanReadibleFn } = getTokenByAddress(pledge.token)
return humanReadibleFn(pledge.amount)
}
export const getAllowanceFromAddress = tokenAddress => {
const token = getTokenByAddress(tokenAddress)
return token.getAllowance()
}
export const getLpAllowance = async contract => {
const { methods: { allowance } } = contract || SNT
const account = await web3.eth.getCoinbase()
const spender = LiquidPledging._address
const allowanceAmt = await allowance(account, spender).call()
return allowanceAmt
}