commit
8bcb3a7e85
6 changed files with 48 additions and 155 deletions
2
.nvmrc
2
.nvmrc
|
|
@ -1 +1 @@
|
||||||
v14.17.6
|
v14.18.3
|
||||||
|
|
|
||||||
|
|
@ -281,7 +281,7 @@ const isAuthenticating = () => _isAuthenticating
|
||||||
const isRegistering = () => _isRegistering
|
const isRegistering = () => _isRegistering
|
||||||
|
|
||||||
const getGun = () => {
|
const getGun = () => {
|
||||||
return gun
|
throw new Error('NO GUNS')
|
||||||
}
|
}
|
||||||
|
|
||||||
const getUser = () => {
|
const getUser = () => {
|
||||||
|
|
|
||||||
157
src/routes.js
157
src/routes.js
|
|
@ -46,7 +46,6 @@ const SESSION_ID = uuid()
|
||||||
module.exports = async (
|
module.exports = async (
|
||||||
_app,
|
_app,
|
||||||
config,
|
config,
|
||||||
mySocketsEvents,
|
|
||||||
{ serverPort, useTLS, CA, CA_KEY, runPrivateKey, runPublicKey, accessSecret }
|
{ serverPort, useTLS, CA, CA_KEY, runPrivateKey, runPublicKey, accessSecret }
|
||||||
) => {
|
) => {
|
||||||
/**
|
/**
|
||||||
|
|
@ -456,21 +455,21 @@ module.exports = async (
|
||||||
try {
|
try {
|
||||||
let { publicKey, deviceId } = req.body
|
let { publicKey, deviceId } = req.body
|
||||||
|
|
||||||
if (Buffer.isBuffer(accessSecret)) {
|
logger.info('Will decrypt public key and device ID for key exchange.')
|
||||||
logger.info('Will decrypt public key and device ID for key exchange.')
|
|
||||||
|
|
||||||
publicKey = await ECCrypto.decrypt(
|
console.log(req.body)
|
||||||
accessSecret,
|
|
||||||
ECC.convertToEncryptedMessage(publicKey)
|
|
||||||
)
|
|
||||||
deviceId = await ECCrypto.decrypt(
|
|
||||||
accessSecret,
|
|
||||||
ECC.convertToEncryptedMessage(deviceId)
|
|
||||||
)
|
|
||||||
|
|
||||||
publicKey = publicKey.toString('utf8')
|
publicKey = await ECCrypto.decrypt(
|
||||||
deviceId = deviceId.toString('utf8')
|
accessSecret,
|
||||||
}
|
ECC.convertToEncryptedMessage(publicKey)
|
||||||
|
)
|
||||||
|
deviceId = await ECCrypto.decrypt(
|
||||||
|
accessSecret,
|
||||||
|
ECC.convertToEncryptedMessage(deviceId)
|
||||||
|
)
|
||||||
|
|
||||||
|
publicKey = publicKey.toString('utf8')
|
||||||
|
deviceId = deviceId.toString('utf8')
|
||||||
|
|
||||||
if (typeof publicKey !== 'string' || !publicKey) {
|
if (typeof publicKey !== 'string' || !publicKey) {
|
||||||
return res.status(500).json({
|
return res.status(500).json({
|
||||||
|
|
@ -527,15 +526,6 @@ module.exports = async (
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
const validateToken = async token => {
|
|
||||||
try {
|
|
||||||
const tokenValid = await auth.validateToken(token)
|
|
||||||
return tokenValid
|
|
||||||
} catch (err) {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the latest channel backups before subscribing.
|
* Get the latest channel backups before subscribing.
|
||||||
*/
|
*/
|
||||||
|
|
@ -626,15 +616,13 @@ module.exports = async (
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
app.post('/api/lnd/auth', async (req, res) => {
|
app.post('/api/lnd/unlock', async (req, res) => {
|
||||||
try {
|
try {
|
||||||
const health = await checkHealth()
|
const health = await checkHealth()
|
||||||
const walletInitialized = await walletExists()
|
const walletInitialized = await walletExists()
|
||||||
const { alias, pass } = req.body
|
const { pass } = req.body
|
||||||
const lndUp = health.LNDStatus.success
|
const lndUp = health.LNDStatus.success
|
||||||
const walletUnlocked = health.LNDStatus.walletStatus === 'unlocked'
|
const walletUnlocked = health.LNDStatus.walletStatus === 'unlocked'
|
||||||
const { authorization = '' } = req.headers
|
|
||||||
const allowUnlockedLND = process.env.ALLOW_UNLOCKED_LND === 'true'
|
|
||||||
const { lightning } = LightningServices.services
|
const { lightning } = LightningServices.services
|
||||||
|
|
||||||
if (!lndUp) {
|
if (!lndUp) {
|
||||||
|
|
@ -647,38 +635,10 @@ module.exports = async (
|
||||||
|
|
||||||
await recreateLnServices()
|
await recreateLnServices()
|
||||||
|
|
||||||
if (GunDB.isAuthenticated()) {
|
|
||||||
GunDB.logoff()
|
|
||||||
}
|
|
||||||
|
|
||||||
const publicKey = await GunDB.authenticate(alias, pass)
|
|
||||||
|
|
||||||
if (!publicKey) {
|
|
||||||
throw new Error('Invalid alias/password combination')
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!walletUnlocked) {
|
if (!walletUnlocked) {
|
||||||
await unlockWallet(pass)
|
await unlockWallet(pass)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (walletUnlocked && !authorization && !allowUnlockedLND) {
|
|
||||||
throw new Error(
|
|
||||||
'Invalid alias/password combination (Untrusted Device)'
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
if (walletUnlocked && !allowUnlockedLND) {
|
|
||||||
const validatedToken = await validateToken(
|
|
||||||
authorization.replace('Bearer ', '')
|
|
||||||
)
|
|
||||||
|
|
||||||
if (!validatedToken) {
|
|
||||||
throw new Error(
|
|
||||||
'Invalid alias/password combination (Untrusted Auth Token)'
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Generate auth token and send it as a JSON response
|
// Generate auth token and send it as a JSON response
|
||||||
const token = await auth.generateToken()
|
const token = await auth.generateToken()
|
||||||
|
|
||||||
|
|
@ -706,23 +666,14 @@ module.exports = async (
|
||||||
}, 1000)
|
}, 1000)
|
||||||
})
|
})
|
||||||
|
|
||||||
saveChannelsBackup()
|
// saveChannelsBackup()
|
||||||
|
// onNewChannelBackup()
|
||||||
// Send an event to update lightning's status
|
// setTimeout(() => {
|
||||||
mySocketsEvents.emit('updateLightning')
|
// channelRequest()
|
||||||
|
// }, 30 * 1000)
|
||||||
onNewChannelBackup()
|
|
||||||
|
|
||||||
setTimeout(() => {
|
|
||||||
channelRequest()
|
|
||||||
}, 30 * 1000)
|
|
||||||
|
|
||||||
res.json({
|
res.json({
|
||||||
authorization: token,
|
authorization: token
|
||||||
user: {
|
|
||||||
alias,
|
|
||||||
publicKey
|
|
||||||
}
|
|
||||||
})
|
})
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
logger.error('Unlock Error:', err)
|
logger.error('Unlock Error:', err)
|
||||||
|
|
@ -739,17 +690,11 @@ module.exports = async (
|
||||||
app.post('/api/lnd/wallet', async (req, res) => {
|
app.post('/api/lnd/wallet', async (req, res) => {
|
||||||
try {
|
try {
|
||||||
const { walletUnlocker } = LightningServices.services
|
const { walletUnlocker } = LightningServices.services
|
||||||
const { password, alias } = req.body
|
const { password } = req.body
|
||||||
const healthResponse = await checkHealth()
|
const healthResponse = await checkHealth()
|
||||||
|
const walletInitialized = await walletExists()
|
||||||
const isUnlocked = healthResponse.LNDStatus.service !== 'walletUnlocker'
|
const isUnlocked = healthResponse.LNDStatus.service !== 'walletUnlocker'
|
||||||
|
|
||||||
if (!alias) {
|
|
||||||
return res.status(400).json({
|
|
||||||
field: 'alias',
|
|
||||||
errorMessage: 'Please specify an alias for your new wallet'
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!password) {
|
if (!password) {
|
||||||
return res.status(400).json({
|
return res.status(400).json({
|
||||||
field: 'password',
|
field: 'password',
|
||||||
|
|
@ -765,8 +710,8 @@ module.exports = async (
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isUnlocked) {
|
if (walletInitialized || isUnlocked) {
|
||||||
throw new Error('Wallet is already unlocked')
|
throw new Error('A wallet already exists')
|
||||||
}
|
}
|
||||||
|
|
||||||
const [genSeedErr, genSeedResponse] = await new Promise(res => {
|
const [genSeedErr, genSeedResponse] = await new Promise(res => {
|
||||||
|
|
@ -795,15 +740,6 @@ module.exports = async (
|
||||||
cipher_seed_mnemonic: mnemonicPhrase
|
cipher_seed_mnemonic: mnemonicPhrase
|
||||||
}
|
}
|
||||||
|
|
||||||
// Register user before creating wallet
|
|
||||||
const publicKey = await GunDB.register(alias, password)
|
|
||||||
|
|
||||||
await GunActions.saveSeedBackup(
|
|
||||||
mnemonicPhrase,
|
|
||||||
GunDB.getUser(),
|
|
||||||
GunDB.mySEA
|
|
||||||
)
|
|
||||||
|
|
||||||
const [initWalletErr, initWalletResponse] = await new Promise(res => {
|
const [initWalletErr, initWalletResponse] = await new Promise(res => {
|
||||||
walletUnlocker.initWallet(
|
walletUnlocker.initWallet(
|
||||||
walletArgs,
|
walletArgs,
|
||||||
|
|
@ -850,11 +786,7 @@ module.exports = async (
|
||||||
}, 30 * 1000)
|
}, 30 * 1000)
|
||||||
return res.json({
|
return res.json({
|
||||||
mnemonicPhrase,
|
mnemonicPhrase,
|
||||||
authorization: token,
|
authorization: token
|
||||||
user: {
|
|
||||||
alias,
|
|
||||||
publicKey
|
|
||||||
}
|
|
||||||
})
|
})
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
logger.error(err)
|
logger.error(err)
|
||||||
|
|
@ -2707,42 +2639,7 @@ module.exports = async (
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
const [relayId, relayUrl, accessSecret] = await Promise.all([
|
throw new Error('')
|
||||||
Storage.getItem('relay/id'),
|
|
||||||
Storage.getItem('relay/url'),
|
|
||||||
Storage.getItem('FirstAccessSecret')
|
|
||||||
])
|
|
||||||
const response = {}
|
|
||||||
if (config.cliArgs.tunnel) {
|
|
||||||
if (!relayId || !relayUrl) {
|
|
||||||
response.relayNotFound = true
|
|
||||||
} else {
|
|
||||||
response.relayId = relayId
|
|
||||||
response.relayUrl = relayUrl
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
response.tunnelDisabled = true
|
|
||||||
}
|
|
||||||
|
|
||||||
if (process.env.ALLOW_UNLOCKED_LND !== 'true') {
|
|
||||||
response.accessSecretDisabled = true
|
|
||||||
return res.json(response)
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!accessSecret) {
|
|
||||||
response.accessCodeNotFound = true
|
|
||||||
res.json(response)
|
|
||||||
return
|
|
||||||
}
|
|
||||||
const codeUsed = await Storage.getItem(
|
|
||||||
`UnlockedAccessSecrets/${accessSecret}`
|
|
||||||
)
|
|
||||||
if (codeUsed !== false) {
|
|
||||||
response.accessCodeUsed = true
|
|
||||||
return res.json(response)
|
|
||||||
}
|
|
||||||
response.accessCode = accessSecret
|
|
||||||
res.json(response)
|
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
logger.error(e)
|
logger.error(e)
|
||||||
res.status(500).json({
|
res.status(500).json({
|
||||||
|
|
|
||||||
|
|
@ -54,7 +54,8 @@ const server = program => {
|
||||||
* exchange. Neither the tunnel nor the WWW should see this private key, it
|
* exchange. Neither the tunnel nor the WWW should see this private key, it
|
||||||
* should only be served through STDOUT (via QR or else).
|
* should only be served through STDOUT (via QR or else).
|
||||||
*/
|
*/
|
||||||
const accessSecret = program.tunnel ? ECCrypto.generatePrivate() : null
|
const accessSecret = ECCrypto.generatePrivate()
|
||||||
|
const accessSecretBase64 = accessSecret.toString('base64')
|
||||||
|
|
||||||
// load app default configuration data
|
// load app default configuration data
|
||||||
const defaults = require('../config/defaults')(program.mainnet)
|
const defaults = require('../config/defaults')(program.mainnet)
|
||||||
|
|
@ -342,8 +343,6 @@ const server = program => {
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
const Sockets = require('./sockets')(io)
|
|
||||||
|
|
||||||
require('./routes')(
|
require('./routes')(
|
||||||
app,
|
app,
|
||||||
{
|
{
|
||||||
|
|
@ -351,7 +350,6 @@ const server = program => {
|
||||||
lndAddress: program.lndAddress,
|
lndAddress: program.lndAddress,
|
||||||
cliArgs: program
|
cliArgs: program
|
||||||
},
|
},
|
||||||
Sockets,
|
|
||||||
{
|
{
|
||||||
serverPort,
|
serverPort,
|
||||||
useTLS: program.useTLS,
|
useTLS: program.useTLS,
|
||||||
|
|
@ -399,30 +397,29 @@ const server = program => {
|
||||||
const dataToQr = JSON.stringify({
|
const dataToQr = JSON.stringify({
|
||||||
URI: `https://${params.relayId}@${noProtocolAddress}`,
|
URI: `https://${params.relayId}@${noProtocolAddress}`,
|
||||||
// Null-check is just to please typescript
|
// Null-check is just to please typescript
|
||||||
accessSecret: accessSecret && accessSecret.toString('base64')
|
accessSecret: accessSecretBase64
|
||||||
})
|
})
|
||||||
qrcode.generate(dataToQr, { small: false })
|
qrcode.generate(dataToQr, { small: false })
|
||||||
logger.info(`connect to ${params.relayId}@${noProtocolAddress}:443`)
|
logger.info(`connect to ${params.relayId}@${noProtocolAddress}:443`)
|
||||||
|
console.log('\n')
|
||||||
|
console.log(`Here's your access secret:`)
|
||||||
|
console.log('\n')
|
||||||
|
console.log(accessSecretBase64)
|
||||||
|
console.log('\n')
|
||||||
|
console.log('\n')
|
||||||
} else {
|
} else {
|
||||||
logger.error('!! Relay did not connect to server !!')
|
logger.error('!! Relay did not connect to server !!')
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
} else {
|
||||||
|
console.log('\n')
|
||||||
|
console.log(`Here's your access secret:`)
|
||||||
|
console.log('\n')
|
||||||
|
console.log(accessSecretBase64)
|
||||||
|
console.log('\n')
|
||||||
|
console.log('\n')
|
||||||
}
|
}
|
||||||
|
|
||||||
if (process.env.ALLOW_UNLOCKED_LND === 'true') {
|
|
||||||
const codes = await Storage.valuesWithKeyMatch(
|
|
||||||
/^UnlockedAccessSecrets\//u
|
|
||||||
)
|
|
||||||
if (codes.length === 0) {
|
|
||||||
const code = ECC.generateRandomString(12)
|
|
||||||
await Storage.setItem(`UnlockedAccessSecrets/${code}`, false)
|
|
||||||
await Storage.setItem(`FirstAccessSecret`, code)
|
|
||||||
logger.info('the access code is:' + code)
|
|
||||||
} else if (codes.length === 1 && codes[0] === false) {
|
|
||||||
const firstCode = await Storage.getItem('FirstAccessSecret')
|
|
||||||
logger.info('the access code is:' + firstCode)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
serverInstance.listen(serverPort, serverHost)
|
serverInstance.listen(serverPort, serverHost)
|
||||||
logger.info('App listening on ' + serverHost + ' port ' + serverPort)
|
logger.info('App listening on ' + serverHost + ' port ' + serverPort)
|
||||||
// @ts-expect-error
|
// @ts-expect-error
|
||||||
|
|
|
||||||
|
|
@ -734,7 +734,7 @@ function createUserReplica() {
|
||||||
*/
|
*/
|
||||||
const Gun = opts => {
|
const Gun = opts => {
|
||||||
lastOpts = opts
|
lastOpts = opts
|
||||||
forge()
|
// forge()
|
||||||
|
|
||||||
return createReplica('$root')
|
return createReplica('$root')
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -8,9 +8,8 @@ module.exports = {
|
||||||
'/favicon.ico': true,
|
'/favicon.ico': true,
|
||||||
'/api/lnd/connect': true,
|
'/api/lnd/connect': true,
|
||||||
'/api/lnd/wallet/status': true,
|
'/api/lnd/wallet/status': true,
|
||||||
'/api/lnd/auth': true,
|
|
||||||
//
|
//
|
||||||
'/api/gun/auth': true,
|
'/api/gunw': true,
|
||||||
'/api/subscribeStream': true,
|
'/api/subscribeStream': true,
|
||||||
'/': true,
|
'/': true,
|
||||||
'/api/accessInfo': true,
|
'/api/accessInfo': true,
|
||||||
|
|
@ -20,7 +19,7 @@ module.exports = {
|
||||||
'/api/lnd/connect': true,
|
'/api/lnd/connect': true,
|
||||||
'/api/lnd/wallet': true,
|
'/api/lnd/wallet': true,
|
||||||
'/api/lnd/wallet/existing': true,
|
'/api/lnd/wallet/existing': true,
|
||||||
'/api/lnd/auth': true,
|
'/api/lnd/unlock': true,
|
||||||
'/api/security/exchangeKeys': true,
|
'/api/security/exchangeKeys': true,
|
||||||
'/api/encryption/exchange': true
|
'/api/encryption/exchange': true
|
||||||
},
|
},
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue