aboutsummaryrefslogtreecommitdiffstats
path: root/app/scripts/lib
diff options
context:
space:
mode:
Diffstat (limited to 'app/scripts/lib')
-rw-r--r--app/scripts/lib/ens-ipfs/contracts/registrar.js (renamed from app/scripts/lib/contracts/registrar.js)0
-rw-r--r--app/scripts/lib/ens-ipfs/contracts/resolver.js (renamed from app/scripts/lib/contracts/resolver.js)0
-rw-r--r--app/scripts/lib/ens-ipfs/resolver.js54
-rw-r--r--app/scripts/lib/ens-ipfs/setup.js63
-rw-r--r--app/scripts/lib/ipfsContent.js46
-rw-r--r--app/scripts/lib/reportFailedTxToSentry.js6
-rw-r--r--app/scripts/lib/resolver.js71
-rw-r--r--app/scripts/lib/setupFetchDebugging.js10
-rw-r--r--app/scripts/lib/setupSentry.js (renamed from app/scripts/lib/setupRaven.js)75
9 files changed, 162 insertions, 163 deletions
diff --git a/app/scripts/lib/contracts/registrar.js b/app/scripts/lib/ens-ipfs/contracts/registrar.js
index 99ca24458..99ca24458 100644
--- a/app/scripts/lib/contracts/registrar.js
+++ b/app/scripts/lib/ens-ipfs/contracts/registrar.js
diff --git a/app/scripts/lib/contracts/resolver.js b/app/scripts/lib/ens-ipfs/contracts/resolver.js
index 1bf3f90ce..1bf3f90ce 100644
--- a/app/scripts/lib/contracts/resolver.js
+++ b/app/scripts/lib/ens-ipfs/contracts/resolver.js
diff --git a/app/scripts/lib/ens-ipfs/resolver.js b/app/scripts/lib/ens-ipfs/resolver.js
new file mode 100644
index 000000000..fe2dc1134
--- /dev/null
+++ b/app/scripts/lib/ens-ipfs/resolver.js
@@ -0,0 +1,54 @@
+const namehash = require('eth-ens-namehash')
+const multihash = require('multihashes')
+const Eth = require('ethjs-query')
+const EthContract = require('ethjs-contract')
+const registrarAbi = require('./contracts/registrar')
+const resolverAbi = require('./contracts/resolver')
+
+module.exports = resolveEnsToIpfsContentId
+
+
+async function resolveEnsToIpfsContentId ({ provider, name }) {
+ const eth = new Eth(provider)
+ const hash = namehash.hash(name)
+ const contract = new EthContract(eth)
+ // lookup registrar
+ const chainId = Number.parseInt(await eth.net_version(), 10)
+ const registrarAddress = getRegistrarForChainId(chainId)
+ if (!registrarAddress) {
+ throw new Error(`EnsIpfsResolver - no known ens-ipfs registrar for chainId "${chainId}"`)
+ }
+ const Registrar = contract(registrarAbi).at(registrarAddress)
+ // lookup resolver
+ const resolverLookupResult = await Registrar.resolver(hash)
+ const resolverAddress = resolverLookupResult[0]
+ if (hexValueIsEmpty(resolverAddress)) {
+ throw new Error(`EnsIpfsResolver - no resolver found for name "${name}"`)
+ }
+ const Resolver = contract(resolverAbi).at(resolverAddress)
+ // lookup content id
+ const contentLookupResult = await Resolver.content(hash)
+ const contentHash = contentLookupResult[0]
+ if (hexValueIsEmpty(contentHash)) {
+ throw new Error(`EnsIpfsResolver - no content ID found for name "${name}"`)
+ }
+ const nonPrefixedHex = contentHash.slice(2)
+ const buffer = multihash.fromHexString(nonPrefixedHex)
+ const contentId = multihash.toB58String(multihash.encode(buffer, 'sha2-256'))
+ return contentId
+}
+
+function hexValueIsEmpty(value) {
+ return [undefined, null, '0x', '0x0', '0x0000000000000000000000000000000000000000000000000000000000000000'].includes(value)
+}
+
+function getRegistrarForChainId (chainId) {
+ switch (chainId) {
+ // mainnet
+ case 1:
+ return '0x314159265dd8dbb310642f98f50c066173c1259b'
+ // ropsten
+ case 3:
+ return '0x112234455c3a32fd11230c42e7bccd4a84e02010'
+ }
+}
diff --git a/app/scripts/lib/ens-ipfs/setup.js b/app/scripts/lib/ens-ipfs/setup.js
new file mode 100644
index 000000000..45eb1ce14
--- /dev/null
+++ b/app/scripts/lib/ens-ipfs/setup.js
@@ -0,0 +1,63 @@
+const urlUtil = require('url')
+const extension = require('extensionizer')
+const resolveEnsToIpfsContentId = require('./resolver.js')
+
+const supportedTopLevelDomains = ['eth']
+
+module.exports = setupEnsIpfsResolver
+
+function setupEnsIpfsResolver({ provider }) {
+
+ // install listener
+ const urlPatterns = supportedTopLevelDomains.map(tld => `*://*.${tld}/*`)
+ extension.webRequest.onErrorOccurred.addListener(webRequestDidFail, { urls: urlPatterns })
+
+ // return api object
+ return {
+ // uninstall listener
+ remove () {
+ extension.webRequest.onErrorOccurred.removeListener(webRequestDidFail)
+ },
+ }
+
+ async function webRequestDidFail (details) {
+ const { tabId, url } = details
+ // ignore requests that are not associated with tabs
+ if (tabId === -1) return
+ // parse ens name
+ const urlData = urlUtil.parse(url)
+ const { hostname: name, path, search } = urlData
+ const domainParts = name.split('.')
+ const topLevelDomain = domainParts[domainParts.length - 1]
+ // if unsupported TLD, abort
+ if (!supportedTopLevelDomains.includes(topLevelDomain)) return
+ // otherwise attempt resolve
+ attemptResolve({ tabId, name, path, search })
+ }
+
+ async function attemptResolve({ tabId, name, path, search }) {
+ extension.tabs.update(tabId, { url: `loading.html` })
+ try {
+ const ipfsContentId = await resolveEnsToIpfsContentId({ provider, name })
+ let url = `https://gateway.ipfs.io/ipfs/${ipfsContentId}${path}${search || ''}`
+ try {
+ // check if ipfs gateway has result
+ const response = await fetch(url, { method: 'HEAD' })
+ // if failure, redirect to 404 page
+ if (response.status !== 200) {
+ extension.tabs.update(tabId, { url: '404.html' })
+ return
+ }
+ // otherwise redirect to the correct page
+ extension.tabs.update(tabId, { url })
+ } catch (err) {
+ console.warn(err)
+ // if HEAD fetch failed, redirect so user can see relevant error page
+ extension.tabs.update(tabId, { url })
+ }
+ } catch (err) {
+ console.warn(err)
+ extension.tabs.update(tabId, { url: `error.html?name=${name}` })
+ }
+ }
+}
diff --git a/app/scripts/lib/ipfsContent.js b/app/scripts/lib/ipfsContent.js
deleted file mode 100644
index 8b08453c4..000000000
--- a/app/scripts/lib/ipfsContent.js
+++ /dev/null
@@ -1,46 +0,0 @@
-const extension = require('extensionizer')
-const resolver = require('./resolver.js')
-
-module.exports = function (provider) {
- function ipfsContent (details) {
- const name = details.url.substring(7, details.url.length - 1)
- let clearTime = null
- if (/^.+\.eth$/.test(name) === false) return
-
- extension.tabs.query({active: true}, tab => {
- extension.tabs.update(tab.id, { url: 'loading.html' })
-
- clearTime = setTimeout(() => {
- return extension.tabs.update(tab.id, { url: '404.html' })
- }, 60000)
-
- resolver.resolve(name, provider).then(ipfsHash => {
- clearTimeout(clearTime)
- let url = 'https://ipfs.infura.io/ipfs/' + ipfsHash
- return fetch(url, { method: 'HEAD' }).then(response => response.status).then(statusCode => {
- if (statusCode !== 200) return extension.tabs.update(tab.id, { url: '404.html' })
- extension.tabs.update(tab.id, { url: url })
- })
- .catch(err => {
- url = 'https://ipfs.infura.io/ipfs/' + ipfsHash
- extension.tabs.update(tab.id, {url: url})
- return err
- })
- })
- .catch(err => {
- clearTimeout(clearTime)
- const url = err === 'unsupport' ? 'unsupport' : 'error'
- extension.tabs.update(tab.id, {url: `${url}.html?name=${name}`})
- })
- })
- return { cancel: true }
- }
-
- extension.webRequest.onErrorOccurred.addListener(ipfsContent, {urls: ['*://*.eth/'], types: ['main_frame']})
-
- return {
- remove () {
- extension.webRequest.onErrorOccurred.removeListener(ipfsContent)
- },
- }
-}
diff --git a/app/scripts/lib/reportFailedTxToSentry.js b/app/scripts/lib/reportFailedTxToSentry.js
index df5661e59..de4d57145 100644
--- a/app/scripts/lib/reportFailedTxToSentry.js
+++ b/app/scripts/lib/reportFailedTxToSentry.js
@@ -7,10 +7,10 @@ module.exports = reportFailedTxToSentry
// for sending to sentry
//
-function reportFailedTxToSentry ({ raven, txMeta }) {
+function reportFailedTxToSentry ({ sentry, txMeta }) {
const errorMessage = 'Transaction Failed: ' + extractEthjsErrorMessage(txMeta.err.message)
- raven.captureMessage(errorMessage, {
+ sentry.captureMessage(errorMessage, {
// "extra" key is required by Sentry
- extra: txMeta,
+ extra: { txMeta },
})
}
diff --git a/app/scripts/lib/resolver.js b/app/scripts/lib/resolver.js
deleted file mode 100644
index ff0fed161..000000000
--- a/app/scripts/lib/resolver.js
+++ /dev/null
@@ -1,71 +0,0 @@
-const namehash = require('eth-ens-namehash')
-const multihash = require('multihashes')
-const HttpProvider = require('ethjs-provider-http')
-const Eth = require('ethjs-query')
-const EthContract = require('ethjs-contract')
-const registrarAbi = require('./contracts/registrar')
-const resolverAbi = require('./contracts/resolver')
-
-function ens (name, provider) {
- const eth = new Eth(new HttpProvider(getProvider(provider.type)))
- const hash = namehash.hash(name)
- const contract = new EthContract(eth)
- const Registrar = contract(registrarAbi).at(getRegistrar(provider.type))
- return new Promise((resolve, reject) => {
- if (provider.type === 'mainnet' || provider.type === 'ropsten') {
- Registrar.resolver(hash).then((address) => {
- if (address === '0x0000000000000000000000000000000000000000') {
- reject(null)
- } else {
- const Resolver = contract(resolverAbi).at(address['0'])
- return Resolver.content(hash)
- }
- }).then((contentHash) => {
- if (contentHash['0'] === '0x0000000000000000000000000000000000000000000000000000000000000000') reject(null)
- if (contentHash.ret !== '0x') {
- const hex = contentHash['0'].substring(2)
- const buf = multihash.fromHexString(hex)
- resolve(multihash.toB58String(multihash.encode(buf, 'sha2-256')))
- } else {
- reject(null)
- }
- })
- } else {
- return reject('unsupport')
- }
- })
-}
-
-function getProvider (type) {
- switch (type) {
- case 'mainnet':
- return 'https://mainnet.infura.io/'
- case 'ropsten':
- return 'https://ropsten.infura.io/'
- default:
- return 'http://localhost:8545/'
- }
-}
-
-function getRegistrar (type) {
- switch (type) {
- case 'mainnet':
- return '0x314159265dd8dbb310642f98f50c066173c1259b'
- case 'ropsten':
- return '0x112234455c3a32fd11230c42e7bccd4a84e02010'
- default:
- return '0x0000000000000000000000000000000000000000'
- }
-}
-
-module.exports.resolve = function (name, provider) {
- const path = name.split('.')
- const topLevelDomain = path[path.length - 1]
- if (topLevelDomain === 'eth' || topLevelDomain === 'test') {
- return ens(name, provider)
- } else {
- return new Promise((resolve, reject) => {
- reject(null)
- })
- }
-}
diff --git a/app/scripts/lib/setupFetchDebugging.js b/app/scripts/lib/setupFetchDebugging.js
index dd87b65a6..c1ef22d21 100644
--- a/app/scripts/lib/setupFetchDebugging.js
+++ b/app/scripts/lib/setupFetchDebugging.js
@@ -2,7 +2,7 @@ module.exports = setupFetchDebugging
//
// This is a utility to help resolve cases where `window.fetch` throws a
-// `TypeError: Failed to Fetch` without any stack or context for the request
+// `TypeError: Failed to Fetch` without any stack or context for the request
// https://github.com/getsentry/sentry-javascript/pull/1293
//
@@ -17,9 +17,11 @@ function setupFetchDebugging() {
try {
return await originalFetch.call(window, ...args)
} catch (err) {
- console.warn('FetchDebugger - fetch encountered an Error', err)
- console.warn('FetchDebugger - overriding stack to point of original call')
- err.stack = initialStack
+ if (!err.stack) {
+ console.warn('FetchDebugger - fetch encountered an Error without a stack', err)
+ console.warn('FetchDebugger - overriding stack to point of original call')
+ err.stack = initialStack
+ }
throw err
}
}
diff --git a/app/scripts/lib/setupRaven.js b/app/scripts/lib/setupSentry.js
index e6e511640..69042bc19 100644
--- a/app/scripts/lib/setupRaven.js
+++ b/app/scripts/lib/setupSentry.js
@@ -1,58 +1,55 @@
-const Raven = require('raven-js')
+const Sentry = require('@sentry/browser')
const METAMASK_DEBUG = process.env.METAMASK_DEBUG
const extractEthjsErrorMessage = require('./extractEthjsErrorMessage')
-const PROD = 'https://3567c198f8a8412082d32655da2961d0@sentry.io/273505'
-const DEV = 'https://f59f3dd640d2429d9d0e2445a87ea8e1@sentry.io/273496'
+const SENTRY_DSN_PROD = 'https://3567c198f8a8412082d32655da2961d0@sentry.io/273505'
+const SENTRY_DSN_DEV = 'https://f59f3dd640d2429d9d0e2445a87ea8e1@sentry.io/273496'
-module.exports = setupRaven
+module.exports = setupSentry
-// Setup raven / sentry remote error reporting
-function setupRaven (opts) {
- const { release } = opts
- let ravenTarget
+// Setup sentry remote error reporting
+function setupSentry (opts) {
+ const { release, getState } = opts
+ let sentryTarget
// detect brave
const isBrave = Boolean(window.chrome.ipcRenderer)
if (METAMASK_DEBUG) {
- console.log('Setting up Sentry Remote Error Reporting: DEV')
- ravenTarget = DEV
+ console.log('Setting up Sentry Remote Error Reporting: SENTRY_DSN_DEV')
+ sentryTarget = SENTRY_DSN_DEV
} else {
- console.log('Setting up Sentry Remote Error Reporting: PROD')
- ravenTarget = PROD
+ console.log('Setting up Sentry Remote Error Reporting: SENTRY_DSN_PROD')
+ sentryTarget = SENTRY_DSN_PROD
}
- const client = Raven.config(ravenTarget, {
+ Sentry.init({
+ dsn: sentryTarget,
+ debug: METAMASK_DEBUG,
release,
- transport: function (opts) {
- opts.data.extra.isBrave = isBrave
- const report = opts.data
+ beforeSend: (report) => rewriteReport(report),
+ })
- try {
- // handle error-like non-error exceptions
- rewriteErrorLikeExceptions(report)
- // simplify certain complex error messages (e.g. Ethjs)
- simplifyErrorMessages(report)
- // modify report urls
- rewriteReportUrls(report)
- } catch (err) {
- console.warn(err)
- }
- // make request normally
- client._makeRequest(opts)
- },
+ Sentry.configureScope(scope => {
+ scope.setExtra('isBrave', isBrave)
})
- client.install()
- return Raven
-}
+ function rewriteReport(report) {
+ try {
+ // simplify certain complex error messages (e.g. Ethjs)
+ simplifyErrorMessages(report)
+ // modify report urls
+ rewriteReportUrls(report)
+ // append app state
+ if (getState) {
+ const appState = getState()
+ report.extra.appState = appState
+ }
+ } catch (err) {
+ console.warn(err)
+ }
+ return report
+ }
-function rewriteErrorLikeExceptions (report) {
- // handle errors that lost their error-ness in serialization (e.g. dnode)
- rewriteErrorMessages(report, (errorMessage) => {
- if (!errorMessage.includes('Non-Error exception captured with keys:')) return errorMessage
- if (!(report.extra && report.extra.__serialized__ && report.extra.__serialized__.message)) return errorMessage
- return `Non-Error Exception: ${report.extra.__serialized__.message}`
- })
+ return Sentry
}
function simplifyErrorMessages (report) {