Skip to content

Commit

Permalink
Merge remote-tracking branch 'origin/develop' into fix/recipient-removal
Browse files Browse the repository at this point in the history
  • Loading branch information
yuetloo committed Jul 19, 2023
2 parents 36ae4ac + 50d93d4 commit 8d70f73
Show file tree
Hide file tree
Showing 26 changed files with 806 additions and 463 deletions.
1 change: 1 addition & 0 deletions .husky/pre-push
Original file line number Diff line number Diff line change
Expand Up @@ -9,5 +9,6 @@ export VITE_IPFS_PINNING_JWT=x
export VITE_IPFS_PINNING_URL=x
export VITE_RECIPIENT_REGISTRY_TYPE=simple
export VITE_USER_REGISTRY_TYPE=simple
export VITE_WALLET_CONNECT_PROJECT_ID=1

yarn test:format && yarn test:web && yarn test:lint-i18n
2 changes: 1 addition & 1 deletion contracts/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@clrfund/contracts",
"version": "4.2.3",
"version": "4.2.4",
"license": "GPL-3.0",
"scripts": {
"hardhat": "hardhat",
Expand Down
2 changes: 1 addition & 1 deletion subgraph/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@clrfund/subgraph",
"version": "4.2.3",
"version": "4.2.4",
"repository": "https://github.com/clrfund/monorepo/subgraph",
"keywords": [
"clr.fund",
Expand Down
6 changes: 6 additions & 0 deletions vue-app/.env.example
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,9 @@ VITE_OPERATOR=
# Index of first round to consider
VITE_FIRST_ROUND=

# Default Language
VITE_I18N_LOCALE=

# Google Service Account credentials in JSON format
GOOGLE_APPLICATION_CREDENTIALS=
# Spreadsheet ID to send recipients data
Expand All @@ -77,6 +80,9 @@ VITE_EXPORT_BATCH_SIZE=
# This is only used for netlify function, sponsor.js, to avoid getting the 'fetch not found' error
AWS_LAMBDA_JS_RUNTIME=nodejs18.x

# walletconnect project id
VITE_WALLET_CONNECT_PROJECT_ID=walletconnect_project_id

# This date will be used in the verify landing page. If not set or bad date format, a generic message will be displayed
# format: yyyy-MM-dd e.g. 2023-06-26
VITE_NEXT_ROUND_START_DATE=
Expand Down
9 changes: 5 additions & 4 deletions vue-app/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@clrfund/vue-app",
"version": "4.2.3",
"version": "4.2.4",
"private": true,
"license": "GPL-3.0",
"scripts": {
Expand All @@ -22,12 +22,14 @@
]
},
"dependencies": {
"@clrfund/maci-utils": "^0.0.1",
"@kleros/gtcr-encoder": "1.4.0",
"@openfonts/inter_all": "^1.0.2",
"@vuelidate/core": "^2.0.0",
"@vuelidate/validators": "^2.0.0",
"@vueuse/core": "^9.6.0",
"@walletconnect/web3-provider": "^1.8.0",
"@walletconnect/ethereum-provider": "^2.9.0",
"@walletconnect/modal": "^2.6.0",
"crypto-js": "^4.1.1",
"ethereum-blockies-base64": "^1.0.2",
"ethers": "^5.7.2",
Expand All @@ -48,8 +50,7 @@
"vue-final-modal": "^4.3.0",
"vue-i18n": "9",
"vue-meta": "3.0.0-alpha.8",
"vue-router": "4",
"@clrfund/maci-utils": "^0.0.1"
"vue-router": "4"
},
"devDependencies": {
"@graphql-codegen/cli": "^3.3.0",
Expand Down
8 changes: 7 additions & 1 deletion vue-app/src/App.vue
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@ import { useAppStore, useUserStore, useRecipientStore, useWalletStore } from '@/
import { storeToRefs } from 'pinia'
import { useRoute } from 'vue-router'
import { useMeta } from 'vue-meta'
import type { WalletUser } from '@/stores'
const route = useRoute()
const appStore = useAppStore()
Expand Down Expand Up @@ -183,9 +184,14 @@ onBeforeUnmount(() => {
watch(walletUser, async () => {
try {
if (walletUser.value) {
const user: WalletUser = {
chainId: walletUser.value.chainId,
walletAddress: walletUser.value.walletAddress,
web3Provider: walletUser.value.web3Provider,
}
// make sure factory is loaded
await appStore.loadFactoryInfo()
userStore.loginUser(walletUser.value)
userStore.loginUser(user)
await userStore.loadUserInfo()
await userStore.loadBrightID()
} else {
Expand Down
4 changes: 2 additions & 2 deletions vue-app/src/api/contributions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -77,7 +77,7 @@ export async function getContributionAmount(
}
const data = await sdk.GetContributionsAmount({
fundingRoundAddress: fundingRoundAddress.toLowerCase(),
contributorAddress,
contributorAddress: contributorAddress.toLowerCase(),
})

if (!data.contributions.length) {
Expand Down Expand Up @@ -117,7 +117,7 @@ export async function hasContributorVoted(fundingRoundAddress: string, contribut
}
const data = await sdk.GetContributorVotes({
fundingRoundAddress: fundingRoundAddress.toLowerCase(),
contributorAddress,
contributorAddress: contributorAddress.toLowerCase(),
})
return !!data.fundingRound?.contributors?.[0]?.votes?.length
}
Expand Down
8 changes: 8 additions & 0 deletions vue-app/src/api/core.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,11 @@ if (!rpcUrl) {
throw new Error('Please provide ethereum rpc url for connecting to blockchain')
}

export const walletConnectProjectId = import.meta.env.VITE_WALLET_CONNECT_PROJECT_ID
if (!walletConnectProjectId) {
throw new Error('Please provide wallet connect project id')
}

export const mainnetProvider = new ethers.providers.StaticJsonRpcProvider(import.meta.env.VITE_ETHEREUM_MAINNET_API_URL)
export const provider = new ethers.providers.StaticJsonRpcProvider(rpcUrl)
export const chainId = Number(import.meta.env.VITE_ETHEREUM_API_CHAINID)
Expand Down Expand Up @@ -100,3 +105,6 @@ const deadline = import.meta.env.VITE_RECIPIENT_JOIN_DEADLINE
? DateTime.fromFormat(import.meta.env.VITE_RECIPIENT_JOIN_DEADLINE, 'yyyy-MM-dd', { zone: 'utc' })
: null
export const recipientJoinDeadlineConfig = deadline?.isValid ? deadline : null

// make sure walletconnect qrcode modal is not blocked by the Wallet Modal
export const walletConnectZIndex = import.meta.env.VITE_WALLET_CONNECT_Z_INDEX || '1500'
14 changes: 12 additions & 2 deletions vue-app/src/api/projects.ts
Original file line number Diff line number Diff line change
Expand Up @@ -214,9 +214,9 @@ export async function getLeaderboardProject(
const project = data.projects.find(project => project.id === projectId)

const metadata = project.metadata
const thumbnailHash = metadata.imageHash
const thumbnailHash = metadata.thumbnailImageHash || metadata.imageHash
const thumbnailImageUrl = thumbnailHash ? `${ipfsGatewayUrl}/ipfs/${thumbnailHash}` : undefined
const bannerHash = metadata.imageHash
const bannerHash = metadata.bannerImageHash || metadata.imageHash
const bannerImageUrl = bannerHash ? `${ipfsGatewayUrl}/ipfs/${bannerHash}` : undefined

return {
Expand All @@ -225,6 +225,16 @@ export async function getLeaderboardProject(
name: project.name,
description: metadata.description,
tagline: metadata.tagline,
category: metadata.category,
problemSpace: metadata.problemSpace,
plans: metadata.plans,
teamName: metadata.teamName,
teamDescription: metadata.teamDescription,
githubUrl: metadata.githubUrl,
radicleUrl: metadata.radicleUrl,
websiteUrl: metadata.websiteUrl,
twitterUrl: metadata.twitterUrl,
discordUrl: metadata.discordUrl,
thumbnailImageUrl,
bannerImageUrl,
index: project.recipientIndex,
Expand Down
2 changes: 1 addition & 1 deletion vue-app/src/api/round.ts
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ export async function getCurrentRound(): Promise<string | null> {
const rounds = await getRounds()
const roundIndex = rounds.findIndex(round => isSameAddress(round.address, fundingRoundAddress))

if (roundIndex >= Number(import.meta.env.VITE_FIRST_ROUND || 0)) {
if (roundIndex >= 0) {
return fundingRoundAddress
}
return null
Expand Down
48 changes: 40 additions & 8 deletions vue-app/src/api/rounds.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,17 @@
import sdk from '@/graphql/sdk'
import extraRounds from '@/rounds/rounds.json'
import { chain } from './core'

export interface Round {
index: number
address: string
network?: string
hasLeaderboard: boolean
startTime: number
}

function toRoundId({ network, address }: { network: string; address: string }): string {
return `${network}-${address}`.toLowerCase()
}

//TODO: update to take factory address as a parameter
Expand All @@ -14,16 +20,42 @@ export async function getRounds(): Promise<Round[]> {
//NOTE: why not instantiate the sdk here?
const data = await sdk.GetRounds()

const rounds: Round[] = extraRounds.map(({ address, network }, index): Round => {
return { index, address, network, hasLeaderboard: true }
const rounds: Round[] = extraRounds.map(({ address, network, startTime }, index): Round => {
return { index, address, network, hasLeaderboard: true, startTime }
})

for (const fundingRound of data.fundingRounds) {
rounds.push({
index: rounds.length,
address: fundingRound.id,
hasLeaderboard: false,
})
const leaderboardRounds = new Set(rounds.map(r => toRoundId({ network: r.network || '', address: r.address })))

const firstRound = Number(import.meta.env.VITE_FIRST_ROUND || 0)

for (let roundIndex = 0; roundIndex < data.fundingRounds.length; roundIndex++) {
if (roundIndex < firstRound) {
// filter out cancelled or test rounds
continue
}

const fundingRound = data.fundingRounds[roundIndex]
const address = fundingRound.id
const isLeaderboardRound = leaderboardRounds.has(toRoundId({ network: chain.label, address }))
if (!isLeaderboardRound) {
rounds.push({
index: rounds.length,
address,
hasLeaderboard: false,
startTime: Number(fundingRound.startTime),
})
}
}

return rounds
.sort((a, b) => a.startTime - b.startTime)
.map((r, index) => {
return {
index,
address: r.address,
hasLeaderboard: r.hasLeaderboard,
startTime: r.startTime,
network: r.network,
}
})
}
19 changes: 6 additions & 13 deletions vue-app/src/components/Cart.vue
Original file line number Diff line number Diff line change
Expand Up @@ -245,7 +245,7 @@ import { useModal } from 'vue-final-modal'
import { useRoute } from 'vue-router'
import { getAssetsUrl } from '@/utils/url'
import { useI18n } from 'vue-i18n'
import ErrorModal from './ErrorModal.vue'
import { showError } from '@/utils/modal'
const { t } = useI18n()
Expand Down Expand Up @@ -307,18 +307,11 @@ function removeAll(): void {
appStore.toggleEditSelection(true)
}
function showError(errorMessage: string) {
const { open, close } = useModal({
component: ErrorModal,
attrs: {
errorMessage,
onClose() {
close()
},
},
})
open()
}
onMounted(() => {
if (currentUser.value && !currentUser.value.encryptionKey) {
promptSignagure()
}
})
function promptConnection(): void {
const { open, close } = useModal({
Expand Down
2 changes: 1 addition & 1 deletion vue-app/src/components/FundsNeededWarning.vue
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@
})
}}
</links>
<links v-else :to="chain.bridge">
<links v-else-if="chain.bridge" :to="chain.bridge">
{{
$t('fundsNeededWarning.link2', {
singleTokenNeeded: singleTokenNeeded,
Expand Down
2 changes: 1 addition & 1 deletion vue-app/src/components/ProjectProfile.vue
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@
</div>
<div class="mobile mb2">
<add-to-cart-button v-if="shouldShowCartInput && hasContributeBtn()" :project="project" />
<claim-button :project="project" />
<claim-button v-if="isCurrentRound" :project="project" />
<p v-if="hasUserContributed && !canUserReallocate">
{{ $t('projectProfile.p1') }}
</p>
Expand Down
2 changes: 1 addition & 1 deletion vue-app/src/locales/es.json
Original file line number Diff line number Diff line change
Expand Up @@ -837,7 +837,7 @@
"link3": "Volver"
},
"addToCartButton": {
"input1": "Agregar al carrito",
"input1": "Agregar",
"input2": "En el carrito 🎉"
},
"brightIdWidget": {
Expand Down
1 change: 0 additions & 1 deletion vue-app/src/stores/app.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,6 @@ import { getAssetsUrl } from '@/utils/url'
import { getTokenLogo } from '@/utils/tokens'
import { assert, ASSERT_MISSING_ROUND, ASSERT_MISSING_SIGNATURE, ASSERT_NOT_CONNECTED_WALLET } from '@/utils/assert'
import { Keypair } from '@clrfund/maci-utils'
import { DateTime } from 'luxon'

export type AppState = {
isAppReady: boolean
Expand Down
19 changes: 9 additions & 10 deletions vue-app/src/stores/user.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import { useAppStore } from '@/stores'
import type { WalletUser } from '@/stores'
import { getContributionAmount, hasContributorVoted } from '@/api/contributions'
import type { BigNumber, Signer } from 'ethers'
import { ensLookup } from '@/utils/accounts'
import { ensLookup, isValidSignature } from '@/utils/accounts'
import { UserRegistryType, userRegistryType } from '@/api/core'
import { getBrightId, type BrightId } from '@/api/bright-id'
import { assert, ASSERT_NOT_CONNECTED_WALLET } from '@/utils/assert'
Expand Down Expand Up @@ -44,6 +44,12 @@ export const useUserStore = defineStore('user', {
assert(this.currentUser, ASSERT_NOT_CONNECTED_WALLET)
if (!this.currentUser.encryptionKey) {
const signature = await this.signer.signMessage(LOGIN_MESSAGE)

if (!isValidSignature(signature)) {
// gnosis safe does not return signature in hex string
// show the result as error
throw new Error(signature)
}
this.currentUser.encryptionKey = sha256(signature)
}
},
Expand Down Expand Up @@ -71,15 +77,8 @@ export const useUserStore = defineStore('user', {

let contribution = appStore.contribution
if (!contribution || contribution.isZero()) {
contribution = await getContributionAmount(
appStore.currentRound.fundingRoundAddress,
this.currentUser.walletAddress,
)

const hasVoted = await hasContributorVoted(
appStore.currentRound.fundingRoundAddress,
this.currentUser.walletAddress,
)
contribution = await getContributionAmount(appStore.currentRound.fundingRoundAddress, walletAddress)
const hasVoted = await hasContributorVoted(appStore.currentRound.fundingRoundAddress, walletAddress)

appStore.contribution = contribution
appStore.hasVoted = hasVoted
Expand Down
34 changes: 12 additions & 22 deletions vue-app/src/stores/wallet/connectors/WalletConnectConnector.ts
Original file line number Diff line number Diff line change
@@ -1,32 +1,22 @@
import WalletConnectProvider from '@walletconnect/web3-provider'
import { chainId as rpcChainId, rpcUrl } from '@/api/core'
import { EthereumProvider } from '@walletconnect/ethereum-provider'
import { chainId as rpcChainId, walletConnectProjectId, walletConnectZIndex } from '@/api/core'

export default {
// TODO: add better return type
connect: async (): Promise<any | undefined> => {
const provider = new WalletConnectProvider({
infuraId: import.meta.env.VITE_INFURA_ID,
rpc: {
[rpcChainId]: rpcUrl,
const provider = await EthereumProvider.init({
projectId: walletConnectProjectId,
chains: [rpcChainId],
showQrModal: true,
qrModalOptions: {
themeMode: 'light',
themeVariables: { '--wcm-z-index': walletConnectZIndex },
enableExplorer: true,
},
})

let accounts, chainId
try {
accounts = await provider.enable()
chainId = await provider.request({ method: 'eth_chainId' })
} catch (err) {
if (err.code === 4001) {
// EIP-1193 userRejectedRequest error
// If this happens, the user rejected the connection request.
/* eslint-disable-next-line no-console */
console.log('Please connect to WalletConnect.')
} else {
/* eslint-disable-next-line no-console */
console.error(err)
return
}
}
const accounts = await provider.enable()
const chainId = await provider.request({ method: 'eth_chainId' })

return {
provider,
Expand Down
Loading

0 comments on commit 8d70f73

Please sign in to comment.