refactor: 🚧 Switched to js, fixed bugs
parent
082ea1d5b0
commit
60ea5968ed
|
@ -1,5 +1,4 @@
|
||||||
node_modules/
|
node_modules/
|
||||||
.env
|
.env
|
||||||
docker-compose.override.yml
|
docker-compose.override.yml
|
||||||
build/
|
|
||||||
wallet/
|
wallet/
|
||||||
|
|
|
@ -4,5 +4,4 @@ WORKDIR /usr/local/src
|
||||||
COPY package*.json ./
|
COPY package*.json ./
|
||||||
RUN npm ci --omit=dev
|
RUN npm ci --omit=dev
|
||||||
COPY . .
|
COPY . .
|
||||||
RUN npm run build
|
|
||||||
ENTRYPOINT ["npm", "run", "--"]
|
ENTRYPOINT ["npm", "run", "--"]
|
||||||
|
|
|
@ -0,0 +1,96 @@
|
||||||
|
import dotenv from 'dotenv'
|
||||||
|
import express, { Express, Request, Response } from 'express'
|
||||||
|
import Wallet from 'monero-wallet-rpc-js'
|
||||||
|
(async () => {
|
||||||
|
|
||||||
|
dotenv.config()
|
||||||
|
const WALLET_ACCOUNT_INDEX = Number(process.env.WALLET_ACCOUNT_INDEX)
|
||||||
|
const WALLET_AUTOSAVE_SEC = Number(process.env.WALLET_AUTOSAVE_SEC)
|
||||||
|
const WALLET_REFRESH_SEC = Number(process.env.WALLET_REFRESH_SEC)
|
||||||
|
|
||||||
|
// Load monero wallet
|
||||||
|
let wallet; try {
|
||||||
|
wallet = await new Wallet({
|
||||||
|
url: process.env.WALLET_RPC_URI,
|
||||||
|
filename: process.env.WALLET_FILENAME,
|
||||||
|
password: process.env.WALLET_PASSWORD,
|
||||||
|
address: process.env.WALLET_ADDRESS,
|
||||||
|
viewKey: process.env.WALLET_VIEWKEY,
|
||||||
|
restoreHeight: process.env.WALLET_RESTORE_HEIGHT,
|
||||||
|
})
|
||||||
|
} catch (err) {
|
||||||
|
console.error(`Failed to open wallet: ${err}`)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set auto save
|
||||||
|
if (WALLET_AUTOSAVE_SEC > 0)
|
||||||
|
setInterval(wallet.store(), WALLET_AUTOSAVE_SEC)
|
||||||
|
|
||||||
|
// Set auto refresh
|
||||||
|
try {
|
||||||
|
await wallet.rpc('auto_refresh', {
|
||||||
|
enable:true, period:WALLET_REFRESH_SEC,
|
||||||
|
})
|
||||||
|
} catch (err) {
|
||||||
|
console.error(`Failed to set auto_refresh to ${process.env.WALLET_REFRESH_SEC}: ${err}`)
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
console.log(`Wallet height: ${await wallet.getHeight()}`)
|
||||||
|
} catch (err) {
|
||||||
|
console.error(`Failed to get blockchain height: ${err}`)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Server
|
||||||
|
const app = express()
|
||||||
|
app.use(express.json())
|
||||||
|
app.listen(80)
|
||||||
|
|
||||||
|
|
||||||
|
// Healthchecks
|
||||||
|
app.get('/wallet/height', async (req, res) =>
|
||||||
|
res.send((await wallet.getHeight()).toString())
|
||||||
|
)
|
||||||
|
app.get('/wallet/balance', async (req, res) =>
|
||||||
|
res.send(
|
||||||
|
String((await wallet.getBalance({
|
||||||
|
account_index: WALLET_ACCOUNT_INDEX,
|
||||||
|
})).balance * 0.000000000001)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
// New payment
|
||||||
|
app.post('/payment', async (req, res) => {
|
||||||
|
res.redirect(`/payment/${(await wallet.createAddress({
|
||||||
|
account_index: WALLET_ACCOUNT_INDEX,
|
||||||
|
label: req.body.label,
|
||||||
|
})).address}`)
|
||||||
|
})
|
||||||
|
|
||||||
|
// Check payment
|
||||||
|
app.get('/payment/:addr', async (req, res) => {
|
||||||
|
let subaddr_index; try {
|
||||||
|
subaddr_index = (await wallet.getAddressIndex({
|
||||||
|
address: req.params.addr
|
||||||
|
})).index.minor
|
||||||
|
} catch (err) {
|
||||||
|
console.error(`Failed to get index of subaddress: ${err}`)
|
||||||
|
return res.status(500).sendText('Failed to determine subaddress index!')
|
||||||
|
}
|
||||||
|
let transfers; try {
|
||||||
|
transfers = Object.values(await wallet.getTransfers({
|
||||||
|
in: true,
|
||||||
|
pending: true,
|
||||||
|
failed: true,
|
||||||
|
pool: true,
|
||||||
|
account_index: WALLET_ACCOUNT_INDEX,
|
||||||
|
subaddr_indices: [subaddr_index],
|
||||||
|
})).flat()
|
||||||
|
} catch (err) {
|
||||||
|
console.error(`Failed to get transactions for subaddress: ${err}`)
|
||||||
|
return res.status(500).sendText('Failed to get transactions!')
|
||||||
|
}
|
||||||
|
return res.json(transfers)
|
||||||
|
})
|
||||||
|
|
||||||
|
})()
|
|
@ -1,21 +1,18 @@
|
||||||
{
|
{
|
||||||
"name": "pago",
|
"name": "pago",
|
||||||
"version": "1.0.0",
|
"version": "1.1.1",
|
||||||
"lockfileVersion": 3,
|
"lockfileVersion": 3,
|
||||||
"requires": true,
|
"requires": true,
|
||||||
"packages": {
|
"packages": {
|
||||||
"": {
|
"": {
|
||||||
"name": "pago",
|
"name": "pago",
|
||||||
"version": "1.0.0",
|
"version": "1.1.1",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"dotenv": "^16.4.5",
|
"dotenv": "^16.4.5",
|
||||||
"express": "^4.19.2",
|
"express": "^4.19.2",
|
||||||
"monero-wallet-rpc-js": "^1.2.5",
|
"monero-wallet-rpc-js": "^1.2.9",
|
||||||
"socket.io": "^4.7.5"
|
"socket.io": "^4.7.5"
|
||||||
},
|
|
||||||
"devDependencies": {
|
|
||||||
"typescript": "^5.4.5"
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/@socket.io/component-emitter": {
|
"node_modules/@socket.io/component-emitter": {
|
||||||
|
@ -628,9 +625,9 @@
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/monero-wallet-rpc-js": {
|
"node_modules/monero-wallet-rpc-js": {
|
||||||
"version": "1.2.5",
|
"version": "1.2.9",
|
||||||
"resolved": "https://registry.npmjs.org/monero-wallet-rpc-js/-/monero-wallet-rpc-js-1.2.5.tgz",
|
"resolved": "https://registry.npmjs.org/monero-wallet-rpc-js/-/monero-wallet-rpc-js-1.2.9.tgz",
|
||||||
"integrity": "sha512-AM7VUZIPURhVKUbeaSIagCtDY+7uNx+1++GO9TCylWxh2pbjIwhvJmkXGLBIDJ7mOiR4vhLFa3Ns/q9x/oerFQ==",
|
"integrity": "sha512-NU+2d21beM300MjOiq76eUrma2SugAZqz0CHIg4vuMTdxgZhBy15p5Akz5NBeWBtuEVBQ8CB2yZLIeC22Wy6jg==",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"axios": "^1.6.8"
|
"axios": "^1.6.8"
|
||||||
}
|
}
|
||||||
|
@ -974,19 +971,6 @@
|
||||||
"node": ">= 0.6"
|
"node": ">= 0.6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"node_modules/typescript": {
|
|
||||||
"version": "5.4.5",
|
|
||||||
"resolved": "https://registry.npmjs.org/typescript/-/typescript-5.4.5.tgz",
|
|
||||||
"integrity": "sha512-vcI4UpRgg81oIRUFwR0WSIHKt11nJ7SAVlYNIu+QpqeyXP+gpQJy/Z4+F0aGxSE4MqwjyXvW/TzgkLAx2AGHwQ==",
|
|
||||||
"dev": true,
|
|
||||||
"bin": {
|
|
||||||
"tsc": "bin/tsc",
|
|
||||||
"tsserver": "bin/tsserver"
|
|
||||||
},
|
|
||||||
"engines": {
|
|
||||||
"node": ">=14.17"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"node_modules/undici-types": {
|
"node_modules/undici-types": {
|
||||||
"version": "5.26.5",
|
"version": "5.26.5",
|
||||||
"resolved": "https://registry.npmjs.org/undici-types/-/undici-types-5.26.5.tgz",
|
"resolved": "https://registry.npmjs.org/undici-types/-/undici-types-5.26.5.tgz",
|
||||||
|
|
10
package.json
10
package.json
|
@ -1,11 +1,10 @@
|
||||||
{
|
{
|
||||||
"name": "pago",
|
"name": "pago",
|
||||||
"version": "1.1.0",
|
"version": "1.1.1",
|
||||||
"description": "Lightweight monero payment gateway",
|
"description": "Lightweight monero payment gateway",
|
||||||
"main": "index.js",
|
"main": "index.js",
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"build": "tsc",
|
"start": "node main.js"
|
||||||
"start": "node --no-experimental-fetch './build/main.js'"
|
|
||||||
},
|
},
|
||||||
"repository": {
|
"repository": {
|
||||||
"type": "git",
|
"type": "git",
|
||||||
|
@ -19,10 +18,7 @@
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"dotenv": "^16.4.5",
|
"dotenv": "^16.4.5",
|
||||||
"express": "^4.19.2",
|
"express": "^4.19.2",
|
||||||
"monero-wallet-rpc-js": "^1.2.5",
|
"monero-wallet-rpc-js": "^1.2.9",
|
||||||
"socket.io": "^4.7.5"
|
"socket.io": "^4.7.5"
|
||||||
},
|
|
||||||
"devDependencies": {
|
|
||||||
"typescript": "^5.4.5"
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
15
sample.env
15
sample.env
|
@ -18,23 +18,22 @@ WALLET_FILENAME='pago'
|
||||||
# Wallet password (Change this!)
|
# Wallet password (Change this!)
|
||||||
WALLET_PASSWORD='6vzyEYNW0uGPuIx'
|
WALLET_PASSWORD='6vzyEYNW0uGPuIx'
|
||||||
# Main wallet address (Change this!)
|
# Main wallet address (Change this!)
|
||||||
WALLET_ADDRESS='55bcxMRhBWea6xxsot8moF1rdPprjJR2x4mfnNnTGgBJFgXa4gWXmWAYdUBKiRcJxy9AUAGJEg28DejvWdJU2VgUDrUvCHG'
|
WALLET_ADDRESS='49YQ71oTRA4Vm5t3nfJH3R9CSf99ofbcf8TJPdNvv7rZZSCLvas7vo1W8knBjWcKf7aQiefSgWb4wH6TXurEcD8JUnJxfsZ'
|
||||||
# Viewkey used for the wallet (Change this!)
|
# Viewkey used for the wallet (Change this!)
|
||||||
WALLET_VIEWKEY='03d463f03ae547b11dfdf194a07ff82c14a3c6a3de559bd89c9a5e8dc5e9ae02'
|
WALLET_VIEWKEY='a23474fe2d3ef001b7f0d311d7bb10eb149bbf9c0e206f7f31cc91ab58781809'
|
||||||
# Set this to the blockheight of first transaction
|
# Set this to the blockheight of first transaction
|
||||||
WALLET_RESTORE_HEIGHT=573936
|
WALLET_RESTORE_HEIGHT=3133069
|
||||||
# Which wallet account to use for payments
|
# Which wallet account to use for payments
|
||||||
WALLET_ACCOUNT_INDEX=1
|
WALLET_ACCOUNT_INDEX=1
|
||||||
# Wallet RPC
|
# Wallet RPC
|
||||||
WALLET_RPC_URI='http://pago_wallet:18082'
|
WALLET_RPC_URI='http://pago_wallet:18082'
|
||||||
# Interval to rescan for transactions
|
# Interval to rescan for transactions
|
||||||
WALLET_REFRESH_SEC=1
|
WALLET_REFRESH_SEC=1
|
||||||
# Interval to save wallet
|
# Interval to save wallet (disable with 0)
|
||||||
# Disable autosave with 0
|
|
||||||
WALLET_REFRESH_SEC=10
|
WALLET_REFRESH_SEC=10
|
||||||
# Public remote node
|
# Public remote node (pick one from https://monero.fail/)
|
||||||
# Find one on https://monero.fail/
|
|
||||||
MONERO_DAEMON_HOST='xmr.gf4.pw:443'
|
MONERO_DAEMON_HOST='xmr.gf4.pw:443'
|
||||||
|
# Same as above, different format
|
||||||
MONERO_DAEMON_URI='https://xmr.gf4.pw'
|
MONERO_DAEMON_URI='https://xmr.gf4.pw'
|
||||||
# Local monero daemon (activate in docker-compose.override.yml)
|
# Local node (activate in docker-compose.override.yml)
|
||||||
#MONERO_DAEMON_URI='http://monerod'
|
#MONERO_DAEMON_URI='http://monerod'
|
||||||
|
|
68
src/main.ts
68
src/main.ts
|
@ -1,68 +0,0 @@
|
||||||
import dotenv from 'dotenv'
|
|
||||||
import express, { Express, Request, Response } from 'express'
|
|
||||||
import Wallet from 'monero-wallet-rpc-js'
|
|
||||||
(async () => {
|
|
||||||
|
|
||||||
dotenv.config()
|
|
||||||
|
|
||||||
// Load monero wallet
|
|
||||||
let wallet; try {
|
|
||||||
wallet = await new Wallet({
|
|
||||||
url: process.env.WALLET_RPC_URI,
|
|
||||||
filename: process.env.WALLET_FILENAME,
|
|
||||||
password: process.env.WALLET_PASSWORD,
|
|
||||||
address: process.env.WALLET_ADDRESS,
|
|
||||||
viewKey: process.env.WALLET_VIEWKEY,
|
|
||||||
restoreHeight: process.env.WALLET_RESTORE_HEIGHT,
|
|
||||||
})
|
|
||||||
} catch (err) {
|
|
||||||
console.error(`Failed to open wallet: ${err}`)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Set auto save
|
|
||||||
if (Number(process.env.WALLET_AUTOSAVE_SEC) > 0)
|
|
||||||
setInterval(
|
|
||||||
wallet.store(),
|
|
||||||
Number(process.env.WALLET_AUTOSAVE_SEC)
|
|
||||||
)
|
|
||||||
|
|
||||||
// Set auto refresh
|
|
||||||
try {
|
|
||||||
await wallet.rpc('auto_refresh', {
|
|
||||||
enable: true,
|
|
||||||
period: Number(process.env.WALLET_REFRESH_SEC),
|
|
||||||
})
|
|
||||||
} catch (err) {
|
|
||||||
console.error(`Failed to set auto_refresh to ${process.env.WALLET_REFRESH_SEC}: ${err}`)
|
|
||||||
}
|
|
||||||
|
|
||||||
try {
|
|
||||||
console.log(`Wallet height: ${await wallet.getHeight()}`)
|
|
||||||
} catch (err) {
|
|
||||||
console.error(`Failed to get blockchain height: ${err}`)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Server
|
|
||||||
const app: Express = express()
|
|
||||||
app.use(express.json())
|
|
||||||
app.listen(80)
|
|
||||||
|
|
||||||
|
|
||||||
// Healthchecks
|
|
||||||
app.get('/wallet/height', async (req: Request, res: Response) =>
|
|
||||||
res.send((await wallet.getHeight()).toString())
|
|
||||||
)
|
|
||||||
app.get('/wallet/balance', async (req: Request, res: Response) =>
|
|
||||||
res.send(
|
|
||||||
((await wallet.getBalance()).balance * 0.000000000001)
|
|
||||||
.toString()
|
|
||||||
)
|
|
||||||
)
|
|
||||||
|
|
||||||
// New payment
|
|
||||||
//app.post('/payment', async (req: Request, res: Response) => {
|
|
||||||
// console.log(`New payment created: "${req.body.label}"`)
|
|
||||||
// return res.sendStatus(200)
|
|
||||||
//})
|
|
||||||
|
|
||||||
})()
|
|
|
@ -1,10 +0,0 @@
|
||||||
{
|
|
||||||
"compilerOptions": {
|
|
||||||
"outDir": "./build",
|
|
||||||
"allowJs": true,
|
|
||||||
"target": "es6",
|
|
||||||
"module": "NodeNext",
|
|
||||||
"moduleResolution": "NodeNext"
|
|
||||||
},
|
|
||||||
"include": ["./src/**/*"]
|
|
||||||
}
|
|
Loading…
Reference in New Issue