mirror of
https://github.com/tornadocash/trusted-setup-server.git
synced 2024-11-24 02:46:33 +01:00
Merge pull request #3 from tornadocash/attestationWatcher
Attestation watcher
This commit is contained in:
commit
6dba8a7de8
@ -10,6 +10,11 @@ MYSQL_DATABASE=phase2
|
||||
TWITTER_CONSUMER_KEY=
|
||||
TWITTER_CONSUMER_SECRET=
|
||||
TWITTER_CALLBACK_URL=https://ceremony.tornado.cash/api/oauth_callback/twitter
|
||||
TWITTER_ACCESS_TOKEN_KEY=
|
||||
TWITTER_ACCESS_TOKEN_SECRET=
|
||||
# hashtag should be provided without # sign
|
||||
TWITTER_HASHTAG=
|
||||
TWITTER_INTERVAL_ATTESTATION=300000
|
||||
|
||||
GITHUB_CLIEND_ID=
|
||||
GITHUB_CLIENT_SECRET=
|
||||
|
@ -11,5 +11,4 @@ COPY --from=bin /usr/bin/phase2_verify_contribution /app/server/bin/
|
||||
|
||||
EXPOSE 3000
|
||||
HEALTHCHECK CMD curl -f http://localhost:3000/
|
||||
RUN yarn build
|
||||
CMD ["yarn", "start"]
|
||||
|
@ -10,6 +10,7 @@
|
||||
@import 'components/status';
|
||||
@import 'components/fieldset';
|
||||
@import 'components/form';
|
||||
@import 'components/highlight';
|
||||
|
||||
.wrapper {
|
||||
display: flex;
|
||||
|
@ -10,6 +10,7 @@ $warning: #ff8a00;
|
||||
$black: #2c4538;
|
||||
$danger: #FF0658;
|
||||
$dark: #242424;
|
||||
$pre: $white;
|
||||
$info: $primary-invert;
|
||||
$info-invert: $white;
|
||||
$custom-colors: ("black": ($black, $primary-invert));
|
||||
@ -159,6 +160,8 @@ $pagination-current-color: $primary-invert;
|
||||
$pagination-current-background-color: $primary;
|
||||
$pagination-current-border-color: $primary;
|
||||
|
||||
$pre-background: rgba($primary, 0.104);
|
||||
|
||||
.columns {
|
||||
@include from(576px) {
|
||||
&.is-small {
|
||||
|
@ -25,6 +25,10 @@
|
||||
text-decoration: underline;
|
||||
}
|
||||
}
|
||||
|
||||
ul {
|
||||
list-style: none;
|
||||
}
|
||||
}
|
||||
|
||||
.columns:not(:last-child) {
|
||||
@ -79,6 +83,7 @@
|
||||
.box {
|
||||
background-color: $primary-invert;
|
||||
border-color: #393939;
|
||||
cursor: inherit;
|
||||
|
||||
.title {
|
||||
color: $white;
|
||||
@ -133,6 +138,16 @@
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
&.has-addons .control {
|
||||
&:not(:last-child) {
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
&:last-child {
|
||||
z-index: 10;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.currently {
|
||||
@ -148,4 +163,15 @@
|
||||
margin-bottom: $block-spacing;
|
||||
}
|
||||
}
|
||||
|
||||
> .buttons {
|
||||
&:not(:last-child) {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
|
||||
.button {
|
||||
margin-bottom: 2rem;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
5
assets/styles/components/_highlight.scss
Normal file
5
assets/styles/components/_highlight.scss
Normal file
@ -0,0 +1,5 @@
|
||||
.hljs-comment,
|
||||
.hljs-quote {
|
||||
color: $primary;
|
||||
font-style: italic;
|
||||
}
|
@ -6,7 +6,7 @@
|
||||
</b-navbar-item>
|
||||
</template>
|
||||
<template slot="end">
|
||||
<b-navbar-item href="#">
|
||||
<b-navbar-item tag="router-link" to="/instructions">
|
||||
Instructions
|
||||
</b-navbar-item>
|
||||
<b-navbar-item href="#">
|
||||
|
@ -72,7 +72,7 @@ module.exports = {
|
||||
/*
|
||||
** Plugins to load before mounting the App
|
||||
*/
|
||||
plugins: [{ src: '~plugins/phase2', ssr: false }],
|
||||
plugins: [{ src: '~plugins/phase2', ssr: false }, '~plugins/highlight'],
|
||||
/*
|
||||
** Nuxt.js dev-modules
|
||||
*/
|
||||
@ -123,5 +123,8 @@ module.exports = {
|
||||
server: {
|
||||
port: 3000, // default: 3000
|
||||
host: '0.0.0.0' // default: localhost
|
||||
},
|
||||
env: {
|
||||
hashtag: process.env.TWITTER_HASHTAG
|
||||
}
|
||||
}
|
||||
|
@ -6,7 +6,7 @@
|
||||
"private": true,
|
||||
"scripts": {
|
||||
"dev": "cross-env NODE_ENV=development nodemon server/index.js --watch server",
|
||||
"build": "nuxt build",
|
||||
"build": "cross-env NODE_ENV=production nuxt build",
|
||||
"start": "cross-env NODE_ENV=production node server/index.js",
|
||||
"generate": "nuxt generate",
|
||||
"lint": "eslint --ext .js,.vue --ignore-path .gitignore ."
|
||||
@ -16,6 +16,7 @@
|
||||
"@open-wc/webpack-import-meta-loader": "^0.4.1",
|
||||
"async-mutex": "^0.1.4",
|
||||
"aws-sdk": "^2.610.0",
|
||||
"blake2": "^4.0.0",
|
||||
"body-parser": "^1.19.0",
|
||||
"cross-env": "^5.2.0",
|
||||
"crypto": "^1.0.1",
|
||||
@ -27,7 +28,9 @@
|
||||
"nuxt": "^2.0.0",
|
||||
"nuxt-buefy": "^0.3.2",
|
||||
"oauth": "^0.9.15",
|
||||
"sequelize": "^5.21.3"
|
||||
"sequelize": "^5.21.3",
|
||||
"twitter": "^1.7.1",
|
||||
"vue-highlightjs": "^1.3.3"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@nuxtjs/eslint-config": "^1.0.1",
|
||||
|
@ -4,7 +4,7 @@
|
||||
Hello, <span>@{{ handle }}</span>
|
||||
</h1>
|
||||
<h2 class="subtitle">
|
||||
Do you want to authorize your contribution #{{ contributionIndex }}? Please sign in.
|
||||
{{ title }}
|
||||
</h2>
|
||||
<fieldset :disabled="hideSaveBtn" class="authorize">
|
||||
<Form />
|
||||
@ -27,7 +27,7 @@
|
||||
target="_blank"
|
||||
outlined
|
||||
>
|
||||
Tweet about your contribution
|
||||
Post attestation
|
||||
</b-button>
|
||||
</div>
|
||||
<div v-show="status.type === 'is-danger' || status.type === 'is-success'" class="status">
|
||||
@ -46,7 +46,6 @@ export default {
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
contributionIndex: 1,
|
||||
token: null,
|
||||
status: {
|
||||
type: '',
|
||||
@ -56,8 +55,18 @@ export default {
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
...mapState('user', ['name', 'handle', 'company']),
|
||||
...mapGetters('user', ['isLoggedIn', 'hasErrorName'])
|
||||
...mapState('user', ['name', 'handle', 'company', 'contributionIndex']),
|
||||
...mapGetters('user', ['isLoggedIn', 'hasErrorName']),
|
||||
title() {
|
||||
if (this.status.type === 'is-danger' || !this.contributionIndex) {
|
||||
return null
|
||||
}
|
||||
if (!this.isLoggedIn) {
|
||||
return `Do you want to authorize your contribution #${this.contributionIndex}? Please sign in.`
|
||||
} else {
|
||||
return `Please, specify your name and organization.`
|
||||
}
|
||||
}
|
||||
},
|
||||
async mounted() {
|
||||
this.$root.$emit('enableLoading')
|
||||
@ -90,7 +99,7 @@ export default {
|
||||
body: JSON.stringify(body)
|
||||
})
|
||||
if (response.ok) {
|
||||
this.status.msg = `Your contribution is verified and authorized. Thank you.`
|
||||
this.status.msg = `Your contribution authorized. Now you can post attestation from your twitter account.`
|
||||
this.status.type = 'is-success'
|
||||
this.hideSaveBtn = true
|
||||
} else {
|
||||
@ -118,7 +127,7 @@ export default {
|
||||
})
|
||||
if (response.ok) {
|
||||
const { id } = await response.json()
|
||||
this.contributionIndex = id
|
||||
this.$store.commit('user/SET_CONTRIBUTION_INDEX', id)
|
||||
} else {
|
||||
const error = await response.text()
|
||||
this.status.msg = error
|
||||
|
@ -57,7 +57,9 @@
|
||||
<b-table-column :centered="true" label="Attestation">
|
||||
<a
|
||||
v-if="props.row.attestation"
|
||||
:href="props.row.attestation"
|
||||
:href="
|
||||
`https://${props.row.socialType}.com/${props.row.handle}/status/${props.row.attestation}`
|
||||
"
|
||||
target="_blank"
|
||||
class="button is-icon"
|
||||
>
|
||||
@ -97,7 +99,7 @@
|
||||
</div>
|
||||
</div>
|
||||
<b-dropdown-item
|
||||
v-for="(rows, index) in [3, 10, 15, 20, 50]"
|
||||
v-for="(rows, index) in [10, 25, 50, 100]"
|
||||
:key="index"
|
||||
:value="rows"
|
||||
aria-role="listitem"
|
||||
|
53
pages/instructions.vue
Normal file
53
pages/instructions.vue
Normal file
@ -0,0 +1,53 @@
|
||||
<template>
|
||||
<div class="ceremony">
|
||||
<h1 class="title is-size-1 is-size-2-mobile is-spaced">
|
||||
Instructions
|
||||
</h1>
|
||||
<h2 class="subtitle">
|
||||
Using pure Rust implementation:
|
||||
</h2>
|
||||
<figure class="highlight">
|
||||
<pre v-highlightjs><code class="bash"># Install rust
|
||||
curl -sSf https://sh.rustup.rs | sh
|
||||
|
||||
# Clone the repository with ceremony code
|
||||
git clone -b ceremony https://github.com/tornadocash/phase2-bn254
|
||||
cd phase2-bn254/phase2
|
||||
|
||||
# Run the ceremony
|
||||
cargo run --release --bin tornado</code></pre>
|
||||
</figure>
|
||||
|
||||
<h2 class="subtitle">
|
||||
Using Docker container:
|
||||
</h2>
|
||||
|
||||
<div class="content p">
|
||||
<p>
|
||||
Using this method you will download and compile ceremony source code from our git repo in a
|
||||
stock Rust container. This is not a prebuilt container distribution.
|
||||
</p>
|
||||
<p>
|
||||
First you need to install the docker on your system:
|
||||
<a
|
||||
href="https://download.docker.com/win/stable/Docker%20Desktop%20Installer.exe"
|
||||
target="_blank"
|
||||
>Windows</a
|
||||
>
|
||||
<a href="https://download.docker.com/mac/stable/Docker.dmg" target="_blank">Mac</a>
|
||||
<a href="https://docs.docker.com/install/#supported-platforms" target="_blank">Linux</a>
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<figure class="highlight">
|
||||
<pre v-highlightjs><code class="bash"># Download dockerfile
|
||||
wget https://raw.githubusercontent.com/tornadocash/phase2-bn254/ceremony/Dockerfile
|
||||
|
||||
# Build docker image
|
||||
docker build . -t ceremony
|
||||
|
||||
# Run the ceremony
|
||||
docker run -ti ceremony</code></pre>
|
||||
</figure>
|
||||
</div>
|
||||
</template>
|
@ -30,6 +30,19 @@
|
||||
<div v-show="status.type === 'is-danger' || status.type === 'is-success'" class="status">
|
||||
<div :class="status.type" class="status-message">{{ status.msg }}</div>
|
||||
</div>
|
||||
<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">
|
||||
<b-button @click="copyContributionHash" type="is-primary">Copy</b-button>
|
||||
</p>
|
||||
</b-field>
|
||||
</div>
|
||||
<div v-show="authorizeLink" class="status">
|
||||
You still can authorize your contribution by following this
|
||||
<a :href="authorizeLink" class="has-text-primary">link</a>.
|
||||
</div>
|
||||
|
||||
<div class="buttons is-centered">
|
||||
<b-button
|
||||
@ -42,19 +55,20 @@
|
||||
Make the contribution
|
||||
</b-button>
|
||||
<b-button
|
||||
v-if="status.type === 'is-success'"
|
||||
v-if="status.type === 'is-success' && contributionType !== 'anonymous'"
|
||||
@click="makeTweet"
|
||||
type="is-primary"
|
||||
tag="a"
|
||||
target="_blank"
|
||||
outlined
|
||||
>
|
||||
Tweet about your contribution
|
||||
Post attestation
|
||||
</b-button>
|
||||
</div>
|
||||
<p class="p">
|
||||
If you don’t trust binaries, we encorage you to follow this <a href="">instruction</a> to
|
||||
contribute by compiling from source code. It is very easy!
|
||||
If you don’t 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!
|
||||
</p>
|
||||
</div>
|
||||
</template>
|
||||
@ -77,7 +91,9 @@ export default {
|
||||
status: {
|
||||
type: '',
|
||||
msg: ''
|
||||
}
|
||||
},
|
||||
contributionHash: null,
|
||||
authorizeLink: null
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
@ -160,13 +176,16 @@ export default {
|
||||
body: formData
|
||||
})
|
||||
if (resp.ok) {
|
||||
this.status.msg = 'Your contribution is verified and recorded. Thank you.'
|
||||
this.status.type = 'is-success'
|
||||
const responseData = await resp.json()
|
||||
this.$store.commit('user/SET_CONTRIBUTION_INDEX', responseData.contributionIndex)
|
||||
console.log(
|
||||
`${window.location.origin}/authorize-contribution?token=${responseData.token}`
|
||||
)
|
||||
this.status.msg = 'Your contribution is verified and recorded.'
|
||||
this.status.type = 'is-success'
|
||||
this.contributionHash = responseData.hash
|
||||
if (this.contributionType === 'anonymous') {
|
||||
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`)
|
||||
@ -193,6 +212,14 @@ export default {
|
||||
onAnonymousHandler() {
|
||||
this.logOut()
|
||||
this.contributionType = 'anonymous'
|
||||
},
|
||||
copyContributionHash() {
|
||||
navigator.clipboard.writeText(this.contributionHash).then(() => {
|
||||
this.$buefy.toast.open({
|
||||
message: 'Copied!',
|
||||
type: 'is-primary'
|
||||
})
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
|
4
plugins/highlight.js
Normal file
4
plugins/highlight.js
Normal file
@ -0,0 +1,4 @@
|
||||
import Vue from 'vue'
|
||||
import VueHighlightJS from 'vue-highlightjs'
|
||||
|
||||
Vue.use(VueHighlightJS)
|
98
server/attestationWatcher.js
Normal file
98
server/attestationWatcher.js
Normal file
@ -0,0 +1,98 @@
|
||||
const fs = require('fs')
|
||||
const Twitter = require('twitter')
|
||||
|
||||
const {
|
||||
TWITTER_CONSUMER_KEY,
|
||||
TWITTER_CONSUMER_SECRET,
|
||||
TWITTER_ACCESS_TOKEN_KEY,
|
||||
TWITTER_ACCESS_TOKEN_SECRET,
|
||||
TWITTER_HASHTAG,
|
||||
TWITTER_INTERVAL_ATTESTATION,
|
||||
NODE_ENV
|
||||
} = process.env
|
||||
|
||||
const client = new Twitter({
|
||||
consumer_key: TWITTER_CONSUMER_KEY,
|
||||
consumer_secret: TWITTER_CONSUMER_SECRET,
|
||||
access_token_key: TWITTER_ACCESS_TOKEN_KEY,
|
||||
access_token_secret: TWITTER_ACCESS_TOKEN_SECRET
|
||||
})
|
||||
|
||||
const { Contribution } = require('./models')
|
||||
|
||||
function attestationWatcher() {
|
||||
// get the last saved tweet
|
||||
let initTweet
|
||||
try {
|
||||
initTweet = require('/tmp/lastTweet.json').lastTweet
|
||||
} catch (e) {
|
||||
initTweet = 0
|
||||
}
|
||||
|
||||
const params = {
|
||||
since_id: initTweet,
|
||||
q: `#${TWITTER_HASHTAG} -filter:retweets`,
|
||||
result_type: 'recent',
|
||||
count: 100
|
||||
}
|
||||
|
||||
// search tweets with params
|
||||
client.get('search/tweets', params, async function(error, tweets, response) {
|
||||
if (!error) {
|
||||
for (const tweet of tweets.statuses) {
|
||||
if (NODE_ENV === 'development') {
|
||||
console.log(
|
||||
'\x1B[36m%s\x1B[0m',
|
||||
`${tweet.text} https://twitter.com/${tweet.user.screen_name}/status/${tweet.id_str}`
|
||||
)
|
||||
}
|
||||
|
||||
// find the contribution id in a tweet
|
||||
let matchTweetContributionId = null
|
||||
let tweetContributionId = null
|
||||
|
||||
if ((matchTweetContributionId = tweet.text.match(/#([0-9]+)/))) {
|
||||
tweetContributionId = Number(matchTweetContributionId[1])
|
||||
}
|
||||
|
||||
// if found the contribution id then search a contribution
|
||||
if (tweetContributionId) {
|
||||
// try update the database record by id
|
||||
try {
|
||||
const result = await Contribution.update(
|
||||
{ attestation: tweet.id_str },
|
||||
{
|
||||
where: {
|
||||
id: tweetContributionId,
|
||||
handle: tweet.user.screen_name,
|
||||
attestation: null
|
||||
}
|
||||
}
|
||||
)
|
||||
if (result[0]) {
|
||||
console.log(
|
||||
`Succesful attestation #${tweetContributionId} https://twitter.com/${tweet.user.screen_name}/status/${tweet.id_str}`
|
||||
)
|
||||
}
|
||||
} catch (error) {
|
||||
console.error(error)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// save the last tweet received
|
||||
fs.writeFileSync(
|
||||
'/tmp/lastTweet.json',
|
||||
JSON.stringify({ lastTweet: tweets.search_metadata.max_id_str })
|
||||
)
|
||||
} else {
|
||||
console.error('attestationWatcher error', error)
|
||||
}
|
||||
})
|
||||
|
||||
setTimeout(() => {
|
||||
attestationWatcher()
|
||||
}, TWITTER_INTERVAL_ATTESTATION)
|
||||
}
|
||||
|
||||
module.exports = attestationWatcher
|
@ -34,6 +34,7 @@ const github = new oauth.OAuth2(
|
||||
'login/oauth/authorize',
|
||||
'login/oauth/access_token'
|
||||
)
|
||||
github.useAuthorizationHeaderforGET(true)
|
||||
|
||||
function validateProvider(req, res, next) {
|
||||
const { provider } = req.params
|
||||
@ -175,6 +176,7 @@ router.get('/user_data/', (req, res) => {
|
||||
|
||||
router.get('/logout', (req, res) => {
|
||||
req.session.destroy()
|
||||
res.send('OK')
|
||||
})
|
||||
|
||||
module.exports = router
|
||||
|
@ -8,6 +8,7 @@ const aws = require('aws-sdk')
|
||||
const express = require('express')
|
||||
const { Mutex } = require('async-mutex')
|
||||
const multer = require('multer')
|
||||
const blake2 = require('blake2')
|
||||
|
||||
const mutex = new Mutex()
|
||||
const s3 = new aws.S3()
|
||||
@ -46,9 +47,9 @@ router.get('/challenge', (req, res) => {
|
||||
|
||||
router.get('/contributions', async (req, res) => {
|
||||
const contributions = await Contribution.findAll({
|
||||
attributes: ['id', 'name', 'company', 'handle', 'socialType']
|
||||
attributes: ['id', 'name', 'company', 'handle', 'socialType', 'attestation']
|
||||
})
|
||||
res.json(contributions).send()
|
||||
res.json(contributions)
|
||||
})
|
||||
|
||||
router.post('/response', upload.single('response'), async (req, res) => {
|
||||
@ -83,7 +84,12 @@ router.post('/response', upload.single('response'), async (req, res) => {
|
||||
token = crypto.randomBytes(32).toString('hex')
|
||||
}
|
||||
|
||||
await Contribution.create({ name, company, handle, socialType, token })
|
||||
const contribution = await fs.readFile(`/tmp/tornado/${req.file.filename}`)
|
||||
const blake2Instance = blake2.createHash('blake2b')
|
||||
blake2Instance.update(contribution)
|
||||
const hash = '0x' + blake2Instance.digest('hex')
|
||||
|
||||
await Contribution.create({ name, company, handle, socialType, token, hash })
|
||||
|
||||
console.log('Contribution is correct, uploading to storage')
|
||||
if (process.env.DISABLE_S3 !== 'true') {
|
||||
@ -97,8 +103,8 @@ router.post('/response', upload.single('response'), async (req, res) => {
|
||||
`./server/snark_files/response_${contributionIndex}`
|
||||
)
|
||||
|
||||
console.log('Finished')
|
||||
res.json({ contributionIndex, token })
|
||||
console.log('Finished. The hash of the contribution is', hash)
|
||||
res.json({ contributionIndex, token, hash })
|
||||
} catch (e) {
|
||||
console.error('Got error during save', e)
|
||||
await fs.unlink(`/tmp/tornado/${req.file.filename}`)
|
||||
@ -136,14 +142,13 @@ router.post('/authorize_contribution', async (req, res) => {
|
||||
handle: req.session.handle,
|
||||
socialType: req.session.socialType
|
||||
},
|
||||
{ individualHooks: true, where: { token: req.body.token }, returning: true }
|
||||
{ where: { id: contribution.dataValues.id }, individualHooks: true }
|
||||
)
|
||||
res.send('OK')
|
||||
} catch (e) {
|
||||
console.error('updateError', e)
|
||||
res.status(404).send('Update error')
|
||||
}
|
||||
|
||||
res.send('OK')
|
||||
})
|
||||
|
||||
router.post('/get_contribution_index', async (req, res) => {
|
||||
|
@ -9,23 +9,18 @@ const config = require('../nuxt.config.js')
|
||||
const sessionsController = require('./controllers/authorize')
|
||||
const contributionController = require('./controllers/contribute')
|
||||
const models = require('./models')
|
||||
const attestationWatcher = require('./attestationWatcher')
|
||||
|
||||
const app = express()
|
||||
|
||||
async function start() {
|
||||
config.dev = NODE_ENV !== 'production'
|
||||
await models.sequelize.sync()
|
||||
const nuxt = new Nuxt(config)
|
||||
|
||||
const { host, port } = nuxt.options.server
|
||||
|
||||
// Build only in dev mode
|
||||
if (config.dev) {
|
||||
const builder = new Builder(nuxt)
|
||||
await builder.build()
|
||||
} else {
|
||||
await nuxt.ready()
|
||||
}
|
||||
const builder = new Builder(nuxt)
|
||||
await builder.build()
|
||||
|
||||
app.use(
|
||||
session({
|
||||
secret: process.env.SESSION_SECRET,
|
||||
@ -50,5 +45,8 @@ async function start() {
|
||||
app.listen(port, host, () => {
|
||||
console.log(`Server is running on port ${port}.`)
|
||||
})
|
||||
|
||||
attestationWatcher()
|
||||
console.log('attestationWatcher started')
|
||||
}
|
||||
start()
|
||||
|
@ -24,7 +24,8 @@ module.exports = (sequelize, DataTypes) => {
|
||||
company: DataTypes.STRING,
|
||||
handle: DataTypes.STRING,
|
||||
socialType: DataTypes.STRING,
|
||||
hash: DataTypes.STRING
|
||||
hash: DataTypes.STRING,
|
||||
attestation: DataTypes.STRING
|
||||
},
|
||||
{
|
||||
hooks: {
|
||||
|
@ -53,7 +53,7 @@ const actions = {
|
||||
window.location.replace(`/api/connect/${provider}`)
|
||||
},
|
||||
makeTweet({ state }) {
|
||||
const tweetText = `Just made the contribution %23${state.contributionIndex} to Tornado.cash Trusted Setup Ceremony! 🚀`
|
||||
const tweetText = `Just made the contribution %23${state.contributionIndex} to @TornadoCash Trusted Setup Ceremony! 🚀 %23${process.env.hashtag}`
|
||||
const popUpWindowWidth = 600
|
||||
const popUpWindowHeight = 250
|
||||
const dualScreenLeft = window.screenLeft !== undefined ? window.screenLeft : window.screenX
|
||||
|
74
yarn.lock
74
yarn.lock
@ -1799,6 +1799,13 @@ bindings@^1.5.0:
|
||||
dependencies:
|
||||
file-uri-to-path "1.0.0"
|
||||
|
||||
blake2@^4.0.0:
|
||||
version "4.0.0"
|
||||
resolved "https://registry.yarnpkg.com/blake2/-/blake2-4.0.0.tgz#32ae4c3568ef5ee4d74c50b99d774abf8fff4f60"
|
||||
integrity sha512-PIOc6RXAZYBYcdpyMzI6/SCU3BH8EbmA9vr0BAVyQv48CQTXDN6viHOTM+8KQue2IPsyHNpIR3UDisz8rZDPTA==
|
||||
dependencies:
|
||||
nan "^2.14.0"
|
||||
|
||||
block-stream@*:
|
||||
version "0.0.9"
|
||||
resolved "https://registry.yarnpkg.com/block-stream/-/block-stream-0.0.9.tgz#13ebfe778a03205cfe03751481ebb4b3300c126a"
|
||||
@ -3004,6 +3011,11 @@ decode-uri-component@^0.2.0:
|
||||
resolved "https://registry.yarnpkg.com/decode-uri-component/-/decode-uri-component-0.2.0.tgz#eb3913333458775cb84cd1a1fae062106bb87545"
|
||||
integrity sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=
|
||||
|
||||
deep-extend@^0.5.0:
|
||||
version "0.5.1"
|
||||
resolved "https://registry.yarnpkg.com/deep-extend/-/deep-extend-0.5.1.tgz#b894a9dd90d3023fbf1c55a394fb858eb2066f1f"
|
||||
integrity sha512-N8vBdOa+DF7zkRrDCsaOXoCs/E2fJfx9B9MrKnnSiHNh4ws7eSys6YQE4KvT1cecKmOASYQBhbKjeuDD9lT81w==
|
||||
|
||||
deep-extend@^0.6.0:
|
||||
version "0.6.0"
|
||||
resolved "https://registry.yarnpkg.com/deep-extend/-/deep-extend-0.6.0.tgz#c4fa7c95404a17a9c3e8ca7e1537312b736330ac"
|
||||
@ -4308,7 +4320,7 @@ har-schema@^2.0.0:
|
||||
resolved "https://registry.yarnpkg.com/har-schema/-/har-schema-2.0.0.tgz#a94c2224ebcac04782a0d9035521f24735b7ec92"
|
||||
integrity sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=
|
||||
|
||||
har-validator@~5.1.0:
|
||||
har-validator@~5.1.0, har-validator@~5.1.3:
|
||||
version "5.1.3"
|
||||
resolved "https://registry.yarnpkg.com/har-validator/-/har-validator-5.1.3.tgz#1ef89ebd3e4996557675eed9893110dc350fa080"
|
||||
integrity sha512-sNvOCzEQNr/qrvJgc3UG/kD4QtlHycrzwS+6mfTrrSq97BvaYcPZZI1ZSqGSPR73Cxn4LKTD4PttRwfU7jWq5g==
|
||||
@ -4436,6 +4448,11 @@ hex-color-regex@^1.1.0:
|
||||
resolved "https://registry.yarnpkg.com/hex-color-regex/-/hex-color-regex-1.1.0.tgz#4c06fccb4602fe2602b3c93df82d7e7dbf1a8a8e"
|
||||
integrity sha512-l9sfDFsuqtOqKDsQdqrMRk0U85RZc0RtOR9yPI7mRVOa4FsR/BVnZ0shmQRM96Ji99kYZP/7hn1cedc1+ApsTQ==
|
||||
|
||||
highlight.js@*:
|
||||
version "9.18.1"
|
||||
resolved "https://registry.yarnpkg.com/highlight.js/-/highlight.js-9.18.1.tgz#ed21aa001fe6252bb10a3d76d47573c6539fe13c"
|
||||
integrity sha512-OrVKYz70LHsnCgmbXctv/bfuvntIKDz177h0Co37DQ5jamGZLVmoCVMtjMtNZY3X9DrCcKfklHPNeA0uPZhSJg==
|
||||
|
||||
hmac-drbg@^1.0.0:
|
||||
version "1.0.1"
|
||||
resolved "https://registry.yarnpkg.com/hmac-drbg/-/hmac-drbg-1.0.1.tgz#d2745701025a6c775a6c545793ed502fc0c649a1"
|
||||
@ -5877,7 +5894,7 @@ named-placeholders@^1.1.2:
|
||||
dependencies:
|
||||
lru-cache "^4.1.3"
|
||||
|
||||
nan@^2.12.1, nan@^2.13.2:
|
||||
nan@^2.12.1, nan@^2.13.2, nan@^2.14.0:
|
||||
version "2.14.0"
|
||||
resolved "https://registry.yarnpkg.com/nan/-/nan-2.14.0.tgz#7818f722027b2459a86f0295d434d1fc2336c52c"
|
||||
integrity sha512-INOFj37C7k3AfaNTtX8RhsTw7qRy7eLET14cROi9+5HAVbbHuIWUHEauBv5qT4Av2tWasiTY1Jw6puUNqRJXQg==
|
||||
@ -7405,7 +7422,7 @@ pseudomap@^1.0.2:
|
||||
resolved "https://registry.yarnpkg.com/pseudomap/-/pseudomap-1.0.2.tgz#f052a28da70e618917ef0a8ac34c1ae5a68286b3"
|
||||
integrity sha1-8FKijacOYYkX7wqKw0wa5aaChrM=
|
||||
|
||||
psl@^1.1.24:
|
||||
psl@^1.1.24, psl@^1.1.28:
|
||||
version "1.7.0"
|
||||
resolved "https://registry.yarnpkg.com/psl/-/psl-1.7.0.tgz#f1c4c47a8ef97167dea5d6bbf4816d736e884a3c"
|
||||
integrity sha512-5NsSEDv8zY70ScRnOTn7bK7eanl2MvFrOrS/R6x+dBt5g1ghnj9Zv90kO8GwT8gxcu2ANyFprnFYB85IogIJOQ==
|
||||
@ -7462,7 +7479,7 @@ punycode@^1.2.4, punycode@^1.4.1:
|
||||
resolved "https://registry.yarnpkg.com/punycode/-/punycode-1.4.1.tgz#c0d5a63b2718800ad8e1eb0fa5269c84dd41845e"
|
||||
integrity sha1-wNWmOycYgArY4esPpSachN1BhF4=
|
||||
|
||||
punycode@^2.1.0:
|
||||
punycode@^2.1.0, punycode@^2.1.1:
|
||||
version "2.1.1"
|
||||
resolved "https://registry.yarnpkg.com/punycode/-/punycode-2.1.1.tgz#b58b010ac40c22c5657616c8d2c2c02c7bf479ec"
|
||||
integrity sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==
|
||||
@ -7768,6 +7785,32 @@ repeating@^2.0.0:
|
||||
dependencies:
|
||||
is-finite "^1.0.0"
|
||||
|
||||
request@^2.72.0:
|
||||
version "2.88.2"
|
||||
resolved "https://registry.yarnpkg.com/request/-/request-2.88.2.tgz#d73c918731cb5a87da047e207234146f664d12b3"
|
||||
integrity sha512-MsvtOrfG9ZcrOwAW+Qi+F6HbD0CWXEh9ou77uOb7FM2WPhwT7smM833PzanhJLsgXjN89Ir6V2PczXNnMpwKhw==
|
||||
dependencies:
|
||||
aws-sign2 "~0.7.0"
|
||||
aws4 "^1.8.0"
|
||||
caseless "~0.12.0"
|
||||
combined-stream "~1.0.6"
|
||||
extend "~3.0.2"
|
||||
forever-agent "~0.6.1"
|
||||
form-data "~2.3.2"
|
||||
har-validator "~5.1.3"
|
||||
http-signature "~1.2.0"
|
||||
is-typedarray "~1.0.0"
|
||||
isstream "~0.1.2"
|
||||
json-stringify-safe "~5.0.1"
|
||||
mime-types "~2.1.19"
|
||||
oauth-sign "~0.9.0"
|
||||
performance-now "^2.1.0"
|
||||
qs "~6.5.2"
|
||||
safe-buffer "^5.1.2"
|
||||
tough-cookie "~2.5.0"
|
||||
tunnel-agent "^0.6.0"
|
||||
uuid "^3.3.2"
|
||||
|
||||
request@^2.87.0, request@^2.88.0:
|
||||
version "2.88.0"
|
||||
resolved "https://registry.yarnpkg.com/request/-/request-2.88.0.tgz#9c2fca4f7d35b592efe57c7f0a55e81052124fef"
|
||||
@ -8896,6 +8939,14 @@ tough-cookie@~2.4.3:
|
||||
psl "^1.1.24"
|
||||
punycode "^1.4.1"
|
||||
|
||||
tough-cookie@~2.5.0:
|
||||
version "2.5.0"
|
||||
resolved "https://registry.yarnpkg.com/tough-cookie/-/tough-cookie-2.5.0.tgz#cd9fb2a0aa1d5a12b473bd9fb96fa3dcff65ade2"
|
||||
integrity sha512-nlLsUzgm1kfLXSXfRZMc1KLAugd4hqJHDTvc2hDIwS3mZAfMEuMbc03SujMF+GEcpaX/qboeycw6iO8JwVv2+g==
|
||||
dependencies:
|
||||
psl "^1.1.28"
|
||||
punycode "^2.1.1"
|
||||
|
||||
trim-newlines@^1.0.0:
|
||||
version "1.0.0"
|
||||
resolved "https://registry.yarnpkg.com/trim-newlines/-/trim-newlines-1.0.0.tgz#5887966bb582a4503a41eb524f7d35011815a613"
|
||||
@ -8935,6 +8986,14 @@ tweetnacl@^0.14.3, tweetnacl@~0.14.0:
|
||||
resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-0.14.5.tgz#5ae68177f192d4456269d108afa93ff8743f4f64"
|
||||
integrity sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=
|
||||
|
||||
twitter@^1.7.1:
|
||||
version "1.7.1"
|
||||
resolved "https://registry.yarnpkg.com/twitter/-/twitter-1.7.1.tgz#0762378f1dc1c050e48f666aca904e24b1a962f4"
|
||||
integrity sha1-B2I3jx3BwFDkj2ZqypBOJLGpYvQ=
|
||||
dependencies:
|
||||
deep-extend "^0.5.0"
|
||||
request "^2.72.0"
|
||||
|
||||
type-check@~0.3.2:
|
||||
version "0.3.2"
|
||||
resolved "https://registry.yarnpkg.com/type-check/-/type-check-0.3.2.tgz#5884cab512cf1d355e3fb784f30804b2b520db72"
|
||||
@ -9300,6 +9359,13 @@ vue-eslint-parser@^7.0.0:
|
||||
esquery "^1.0.1"
|
||||
lodash "^4.17.15"
|
||||
|
||||
vue-highlightjs@^1.3.3:
|
||||
version "1.3.3"
|
||||
resolved "https://registry.yarnpkg.com/vue-highlightjs/-/vue-highlightjs-1.3.3.tgz#29a0d57132fc1ce15cfa61e896918f5b718c5d52"
|
||||
integrity sha1-KaDVcTL8HOFc+mHolpGPW3GMXVI=
|
||||
dependencies:
|
||||
highlight.js "*"
|
||||
|
||||
vue-hot-reload-api@^2.3.0:
|
||||
version "2.3.4"
|
||||
resolved "https://registry.yarnpkg.com/vue-hot-reload-api/-/vue-hot-reload-api-2.3.4.tgz#532955cc1eb208a3d990b3a9f9a70574657e08f2"
|
||||
|
Loading…
Reference in New Issue
Block a user