trusted-setup-server/pages/make-contribution.vue

227 lines
7.1 KiB
Vue
Raw Normal View History

<template>
<div class="ceremony">
<h1 class="title is-size-1 is-size-2-mobile is-spaced">
Hello, <span>@{{ userHandle }}</span>
</h1>
2020-02-05 11:53:45 +01:00
<h2 class="subtitle">
What way do you want to contribute to the Tornado.cash Trusted Setup Ceremony?
</h2>
<fieldset :disabled="status.type === 'is-success'">
<div class="columns is-centered">
<div class="column is-one-third">
<button
:class="{ 'is-hovered': contributionType === 'anonymous' }"
@click="onAnonymousHandler"
class="box box-anonymous"
>
<div class="title is-5">Anonymously</div>
<Cloak />
</button>
</div>
<div class="column is-one-third">
<div :class="{ 'is-hovered': isLoggedIn }" class="box">
<div class="title is-5">Using a social account</div>
<Form />
</div>
</div>
</div>
</fieldset>
2020-02-06 12:58:35 +01:00
<div v-show="status.type === 'is-danger' || status.type === 'is-success'" class="status">
<div :class="status.type" class="status-message">{{ status.msg }}</div>
</div>
2020-02-29 13:47:04 +01:00
<div v-show="contributionHash" class="status">
<div class="label">Your contribution hash (Blake2b)</div>
<b-field position="is-centered">
<b-input :value="contributionHash" readonly></b-input>
<p class="control">
2020-02-29 13:54:36 +01:00
<b-button @click="copyContributionHash" type="is-primary">Copy</b-button>
2020-02-29 13:47:04 +01:00
</p>
</b-field>
2020-02-29 12:22:45 +01:00
</div>
2020-02-29 13:47:04 +01:00
<div v-show="authorizeLink" class="status">
You still can authorize your contribution by following this
<a :href="authorizeLink" class="has-text-primary">link</a>.
2020-02-29 12:22:45 +01:00
</div>
<div class="buttons is-centered">
<b-button
2020-02-05 11:53:45 +01:00
v-if="!isContributeBtnSnown"
@click="makeContribution"
2020-02-05 11:53:45 +01:00
:disabled="isContributeBtnDisabled"
type="is-primary"
outlined
>
Make the contribution
</b-button>
<b-button
v-if="status.type === 'is-success' && contributionType !== 'anonymous'"
2020-02-05 11:53:45 +01:00
@click="makeTweet"
type="is-primary"
tag="a"
target="_blank"
outlined
>
2020-02-28 14:38:36 +01:00
Post attestation
</b-button>
</div>
2020-02-05 11:53:45 +01:00
<p class="p">
2020-02-29 16:27:01 +01:00
If you dont trust binaries, we encorage you to follow this
<router-link to="/instructions">instruction</router-link> to contribute by compiling from
source code. It is very easy!
2020-02-05 11:53:45 +01:00
</p>
</div>
</template>
<script>
/* eslint-disable no-console */
import { mapGetters, mapActions } from 'vuex'
import Cloak from '@/components/Cloak'
import Form from '@/components/Form'
const timeout = (ms) => new Promise((resolve) => setTimeout(resolve, ms))
export default {
components: {
Cloak,
Form
},
data() {
return {
2020-02-05 11:53:45 +01:00
isContributeBtnSnown: false,
status: {
type: '',
msg: ''
2020-02-29 12:22:45 +01:00
},
contributionHash: null,
authorizeLink: null
}
},
computed: {
...mapGetters('user', ['isLoggedIn', 'hasErrorName']),
userName: {
get() {
return this.$store.state.user.name
},
set(value) {
this.$store.commit('user/SET_NAME', value)
}
},
userHandle: {
get() {
return this.$store.state.user.handle
},
set(value) {
this.$store.commit('user/SET_HANDLE', value)
}
},
userCompany: {
get() {
return this.$store.state.user.company
},
set(value) {
this.$store.commit('user/SET_COMPANY', value)
}
},
contributionType: {
get() {
return this.$store.state.user.contributionType
},
set(value) {
this.$store.commit('user/SET_CONTRIBUTION_TYPE', value)
}
2020-02-05 11:53:45 +01:00
},
isContributeBtnDisabled() {
return (
!this.contributionType ||
(!this.isLoggedIn && this.contributionType !== 'anonymous') ||
this.hasErrorName.invalid
)
}
},
async mounted() {
this.$root.$emit('enableLoading')
2020-02-06 17:16:38 +01:00
await this.getUserData()
2020-02-08 16:36:03 +01:00
setTimeout(() => {
this.$root.$emit('disableLoading')
2020-02-08 16:36:03 +01:00
}, 800)
},
methods: {
2020-02-06 17:16:38 +01:00
...mapActions('user', ['makeTweet', 'logOut', 'getUserData']),
async makeContribution({ retry = 0 } = {}) {
try {
2020-02-05 11:53:45 +01:00
this.isContributeBtnSnown = true
this.status.msg = ''
this.status.type = ''
this.$root.$emit('enableLoading', 'Downloading last contribution')
let data = await fetch('api/challenge')
data = new Uint8Array(await data.arrayBuffer())
this.$root.$emit('enableLoading', 'Generating random contribution')
await timeout(100) // allow UI to update before freezing in wasm
console.log('Source params', data)
const contribute = await this.$contribute()
const result = contribute(data)
console.log('Updated params', result)
this.$root.$emit('enableLoading', 'Uploading and verifying your contribution')
console.log('this.user.name', this.userName, this.userHandle, this.userCompany)
const formData = new FormData()
formData.append('response', new Blob([result], { type: 'application/octet-stream' }))
2020-02-05 11:53:45 +01:00
if (this.contributionType !== 'anonymous') {
formData.append('name', this.userName)
formData.append('company', this.userCompany)
2020-02-05 11:53:45 +01:00
}
const resp = await fetch('api/response', {
method: 'POST',
body: formData
})
if (resp.ok) {
2020-02-05 16:02:34 +01:00
const responseData = await resp.json()
this.$store.commit('user/SET_CONTRIBUTION_INDEX', responseData.contributionIndex)
this.status.msg = 'Your contribution is verified and recorded.'
this.status.type = 'is-success'
2020-02-29 12:22:45 +01:00
this.contributionHash = responseData.hash
if (this.contributionType === 'anonymous') {
2020-02-29 12:22:45 +01:00
this.authorizeLink = `${window.location.origin}/authorize-contribution?token=${responseData.token}`
} else {
this.status.msg += ' Now you can post attestation from your twitter account.'
}
} else if (resp.status === 422) {
if (retry < 3) {
console.log(`Looks like someone else uploaded contribution ahead of us, retrying`)
await this.makeContribution({ retry: retry++ })
} else {
this.status.msg = `Failed to upload your contribution after ${retry} attempts`
this.status.type = 'is-danger'
2020-02-05 11:53:45 +01:00
this.isContributeBtnSnown = false
}
} else {
this.status.msg = 'Error uploading your contribution'
this.status.type = 'is-danger'
2020-02-05 11:53:45 +01:00
this.isContributeBtnSnown = false
}
} catch (e) {
console.error(e.message)
this.status.msg = e.message
this.status.type = 'is-danger'
2020-02-05 11:53:45 +01:00
this.isContributeBtnSnown = false
2020-02-06 12:58:35 +01:00
} finally {
this.$root.$emit('disableLoading')
}
},
2020-02-05 11:53:45 +01:00
onAnonymousHandler() {
this.logOut()
2020-02-05 11:53:45 +01:00
this.contributionType = 'anonymous'
2020-02-29 13:47:04 +01:00
},
2020-02-29 13:54:36 +01:00
copyContributionHash() {
2020-02-29 13:47:04 +01:00
navigator.clipboard.writeText(this.contributionHash).then(() => {
this.$buefy.toast.open({
message: 'Copied!',
type: 'is-primary'
})
})
}
}
}
</script>