'
4 | labels: [Bug, Triage]
5 | assignees:
6 | - Chef-Cheems
7 | - chef-jojo
8 | body:
9 | - type: checkboxes
10 | attributes:
11 | label: Is there an existing issue for this?
12 | description: Please search to see if an issue already exists for the bug you encountered.
13 | options:
14 | - label: I have searched the existing issues
15 | required: true
16 | - type: dropdown
17 | attributes:
18 | label: Product
19 | description: Which page or product does this relate to?
20 | multiple: false
21 | options:
22 | - Trade
23 | - Farms
24 | - Syrup Pools
25 | - Lottery
26 | - Prediction
27 | - IFO
28 | - Info
29 | - NFT
30 | - Other
31 | validations:
32 | required: true
33 | - type: textarea
34 | attributes:
35 | label: Current Behavior
36 | description: A concise description of what you're experiencing.
37 | validations:
38 | required: true
39 | - type: textarea
40 | attributes:
41 | label: Expected Behavior
42 | description: A concise description of what you expected to happen.
43 | validations:
44 | required: true
45 | - type: textarea
46 | attributes:
47 | label: Steps To Reproduce
48 | description: Steps to reproduce the behavior.
49 | placeholder: |
50 | 1. In this environment...
51 | 2. With this config...
52 | 3. Run '...'
53 | 4. See error...
54 | validations:
55 | required: true
56 | - type: textarea
57 | attributes:
58 | label: Environment
59 | description: |
60 | example 1:
61 | - **Device**: MacBook Pro
62 | - **OS**: Big Sur 11.3.1
63 | - **Brower**: Chome
64 | - **Wallet**: Metamask
65 |
66 | example 2:
67 | - **Device**: IPhone XR
68 | - **OS**: IOS 13
69 | - **Brower**: N/A
70 | - **Wallet**: Metamask app
71 | value: |
72 | - Device:
73 | - OS:
74 | - Browser:
75 | - Wallet:
76 | render: markdown
77 | validations:
78 | required: true
79 | - type: textarea
80 | attributes:
81 | label: Anything else?
82 | description: |
83 | Links? References? Anything that will give us more context about the issue you are encountering!
84 |
85 | Tip: You can attach images by clicking this area to highlight it and then dragging files in.
86 | validations:
87 | required: false
88 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | .env
2 |
3 | .env.local
4 |
5 | .env.testnet
6 |
7 | .env.
8 |
9 | uploads
10 | # Logs
11 | logs
12 | *.log
13 | npm-debug.log*
14 | yarn-debug.log*
15 | yarn-error.log*
16 | lerna-debug.log*
17 | .idea
18 |
19 | # Diagnostic reports (https://nodejs.org/api/report.html)
20 | report.[0-9]*.[0-9]*.[0-9]*.[0-9]*.json
21 |
22 | # Runtime data
23 | pids
24 | *.pid
25 | *.seed
26 | *.pid.lock
27 | .idea
28 |
29 |
30 | # Directory for instrumented libs generated by jscoverage/JSCover
31 | lib-cov
32 |
33 | # Coverage directory used by tools like istanbul
34 | coverage
35 | *.lcov
36 |
37 | # nyc test coverage
38 | .nyc_output
39 |
40 | # Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files)
41 | .grunt
42 |
43 | # Bower dependency directory (https://bower.io/)
44 | bower_components
45 |
46 | # node-waf configuration
47 | .lock-wscript
48 |
49 | # Compiled binary addons (https://nodejs.org/api/addons.html)
50 | build/Release
51 |
52 | # Dependency directories
53 | node_modules/
54 | jspm_packages/
55 |
56 | #config files
57 | conf/wallets/bep20.json
58 | conf/wallets/campaign.json
59 | conf/wallets/campaign.polygon.json
60 | conf/wallets/campaign.arthera.json
61 | conf/ssl/fullchain.pem
62 | conf/ssl/privkey.pem
63 | conf/satt-token-firebase-adminsdk-fwxcj-2215bda3fa.json
64 | # TypeScript v1 declaration files
65 | typings/
66 |
67 | # TypeScript cache
68 | *.tsbuildinfo
69 |
70 | # Optional npm cache directory
71 | .npm
72 |
73 | # Optional eslint cache
74 | .eslintcache
75 |
76 | # Microbundle cache
77 | .rpt2_cache/
78 | .rts2_cache_cjs/
79 | .rts2_cache_es/
80 | .rts2_cache_umd/
81 |
82 | # Optional REPL history
83 | .node_repl_history
84 |
85 | # Output of 'npm pack'
86 | *.tgz
87 |
88 | # Yarn Integrity file
89 | .yarn-integrity
90 |
91 | # dotenv environment variables file
92 |
93 | .env.test
94 | .env
95 |
96 | # parcel-bundler cache (https://parceljs.org/)
97 | .cache
98 |
99 | # Next.js build output
100 | .next
101 |
102 | # Nuxt.js build / generate output
103 | .nuxt
104 | dist
105 |
106 | # Gatsby files
107 | .cache/
108 | # Comment in the public line in if your project uses Gatsby and *not* Next.js
109 | # https://nextjs.org/blog/next-9-1#public-directory-support
110 | # public
111 |
112 | # vuepress build output
113 | .vuepress/dist
114 |
115 | # Serverless directories
116 | .serverless/
117 |
118 | # FuseBox cache
119 | .fusebox/
120 |
121 | # DynamoDB Local files
122 | .dynamodb/
123 |
124 | # TernJS port file
125 | .tern-port
126 |
127 | # Vscode extentions related files
128 | .history
129 | .vscode
130 |
--------------------------------------------------------------------------------
/libs/transfer/transfer-btc.js:
--------------------------------------------------------------------------------
1 | const bip38 = require('bip38')
2 | const wif = require('wif')
3 | const child = require('child_process')
4 | const rp = require('axios');
5 | const bitcoinjs = require('bitcoinjs-lib')
6 | const config = require('./config')
7 |
8 | module.exports.transferBTC = async function ({
9 | to,
10 | amount,
11 | walletPassword,
12 | account,
13 | }) {
14 | var escpass = walletPassword.replace(/'/g, "\\'")
15 |
16 | var priv = bip38.decrypt(account.btc.ek, escpass)
17 |
18 | var encode = wif.encode(0x80, priv.privateKey, priv.compressed)
19 |
20 | var addr = account.btc.addressSegWitCompat
21 |
22 | var utxo = JSON.parse(
23 | child.execSync(
24 | config.BTC_CMD + ' listunspent 1 1000000 \'["' + addr + '"]\''
25 | )
26 | )
27 |
28 | if (!utxo.length) {
29 | return { error: 'insufficient funds ' }
30 | }
31 |
32 | var max = 0.0
33 | for (var i = 0; i < utxo.length; i++) {
34 | max += parseFloat(utxo[i].amount)
35 | }
36 | max = Math.floor(parseFloat(max) * 100000000)
37 |
38 | var body = await rp({ uri: config.BTS_FEES, json: true })
39 | var feeRate = 15 // parseInt(body.fastestFee);
40 |
41 | var maxFee = 20000
42 |
43 | const keyPair = bitcoinjs.ECPair.fromWIF(encode)
44 | const txb = new bitcoinjs.TransactionBuilder()
45 |
46 | var input_sum = 0
47 | var fee = (45 + utxo.length * 93) * feeRate
48 | for (var i = 0; i < utxo.length; i++) {
49 | txb.addInput(utxo[i].txid, parseInt(utxo[i].vout))
50 | input_sum += Math.round(parseFloat(utxo[i].amount) * 100000000)
51 | }
52 | var change = input_sum - parseInt(amount) - (fee + 34 * feeRate)
53 | txb.addOutput(to, parseInt(amount))
54 |
55 | if (change > fee) {
56 | txb.addOutput(addr, parseInt(change))
57 | fee += 34 * feeRate
58 | }
59 |
60 | if (parseInt(amount) + parseInt(fee) > max) {
61 | return {
62 | error: 'insufficient funds for gas',
63 | }
64 | }
65 |
66 | const p2wpkh = bitcoinjs.payments.p2wpkh({ pubkey: keyPair.publicKey })
67 | const p2sh = bitcoinjs.payments.p2sh({ redeem: p2wpkh })
68 |
69 | for (var i = 0; i < utxo.length; i++) {
70 | txb.sign(
71 | i,
72 | keyPair,
73 | p2sh.redeem.output,
74 | null,
75 | Math.round(parseFloat(utxo[i].amount) * 100000000)
76 | )
77 | }
78 | var tx = txb.build()
79 |
80 | var signed = tx.toHex()
81 | var transactionHash = tx.getId()
82 |
83 | var rec = child.execSync(
84 | config.BTC_CMD + ' sendrawtransaction "' + signed + '"'
85 | )
86 | return { transactionHash }
87 | }
88 |
--------------------------------------------------------------------------------
/bin/www:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env node
2 |
3 | /**
4 | * Module dependencies.
5 | */
6 | const ip = require("ip");
7 | exports.ip = ip.address()
8 |
9 | var app = require('../app');
10 | var fs = require('fs')
11 |
12 | var debug = require('debug')('myapp:server')
13 | var https = require('https');
14 | var cluster = require('cluster');
15 |
16 | //Returns an array of objects containing information about each logical CPU core.
17 | var numCPUs = require('os').cpus().length;
18 | /**
19 | * Get port from environment and store in Express.
20 | */
21 |
22 |
23 | var port = normalizePort(process.env.LISTEN_PORT || '3015');
24 | app.set('port', port);
25 |
26 | /**
27 | * Create HTTP server.
28 | */
29 |
30 | var server = https.createServer( {
31 | key: fs.readFileSync(process.env.SSL_KEY, 'utf8'),
32 | cert: fs.readFileSync(process.env.SSL_CER, 'utf8'),
33 | },app);
34 |
35 | if (cluster.isMaster) {
36 | // Fork workers.
37 | for (var i = 0; i < numCPUs; i++) {
38 | cluster.fork();
39 | }
40 |
41 | cluster.on('death', function(worker) {
42 | });
43 | } else {
44 | server.listen(port);
45 | }
46 |
47 | server.on('error', onError);
48 | server.on('listening', onListening);
49 |
50 | /**
51 | * Normalize a port into a number, string, or false.
52 | */
53 |
54 | function normalizePort(val) {
55 | var port = parseInt(val, 10);
56 |
57 | if (isNaN(port)) {
58 | // named pipe
59 | return val;
60 | }
61 |
62 | if (port >= 0) {
63 | // port number
64 | return port;
65 | }
66 |
67 | return false;
68 | }
69 |
70 | /**
71 | * Event listener for HTTP server "error" event.
72 | */
73 |
74 | function onError(error) {
75 | if (error.syscall !== 'listen') {
76 | throw error;
77 | }
78 |
79 | var bind = typeof port === 'string' ?
80 | 'Pipe ' + port :
81 | 'Port ' + port;
82 |
83 | // handle specific listen errors with friendly messages
84 | switch (error.code) {
85 | case 'EACCES':
86 | console.error(bind + ' requires elevated privileges');
87 | process.exit(1);
88 | break;
89 | case 'EADDRINUSE':
90 | console.error(bind + ' is already in use');
91 | process.exit(1);
92 | break;
93 | default:
94 | throw error;
95 | }
96 | }
97 |
98 | /**
99 | * Event listener for HTTP server "listening" event.
100 | */
101 |
102 | function onListening() {
103 | var addr = server.address();
104 | var bind = typeof addr === 'string' ?
105 | 'pipe ' + addr :
106 | 'port ' + addr.port;
107 | debug('Listening on ' + bind);
108 | }
--------------------------------------------------------------------------------
/model/campaigns.model.js:
--------------------------------------------------------------------------------
1 | const mongoose = require('mongoose')
2 |
3 | const campaignsSchema = mongoose.Schema(
4 | {
5 | title: { type: String },
6 | description: { type: String },
7 | resume: { type: String },
8 | brand: { type: String },
9 | reference: { type: String },
10 | countries: [
11 | {
12 | item_id: { type: Number },
13 | item_text: { type: String },
14 | },
15 | ],
16 | token: {
17 | name: { type: String },
18 | type: { type: String },
19 | addr: { type: String },
20 | },
21 | tags: [{ type: String }],
22 | endDate: { type: mongoose.Schema.Types.Mixed },
23 | startDate: { type: mongoose.Schema.Types.Mixed },
24 | remuneration: { type: String },
25 | ratios: [
26 | {
27 | like: { type: String },
28 | view: { type: String },
29 | share: { type: String },
30 | reachLimit: { type: String },
31 | oracle: { type: String },
32 | },
33 | ],
34 | bounties: [
35 | {
36 | oracle: { type: String },
37 | categories: [
38 | {
39 | minFollowers: { type: Number },
40 | maxFollowers: { type: Number },
41 | reward: { type: String },
42 | },
43 | ],
44 | },
45 | ],
46 | missions: [
47 | {
48 | oracle: { type: String },
49 | sub_missions: [
50 | {
51 | mission: { type: String },
52 | },
53 | ],
54 | },
55 | ],
56 | cost: { type: String },
57 | cost_usd: { type: String },
58 | idNode: { type: String },
59 | type: { type: String },
60 | cover: { type: String },
61 | logo: { type: String },
62 | coverSrc: { type: String },
63 | coverMobile: { type: String },
64 | coverSrcMobile: { type: String },
65 | contract: { type: String },
66 | limit : {type : Number, default : 0},
67 | dataUrl: { type: String },
68 | funds: [{ type: String }, { type: String }],
69 | hash: { type: String },
70 | transactionHash: { type: String },
71 | walletId: { type: String },
72 | launchDate : { type: Date },
73 | retrieved: {type : Boolean}
74 |
75 | },
76 | { timestamps: true, collection: 'campaigns' }
77 | )
78 |
79 | const Campaigns = mongoose.model('campaigns', campaignsSchema)
80 |
81 | module.exports = Campaigns
82 |
--------------------------------------------------------------------------------
/model/wallet.model.js:
--------------------------------------------------------------------------------
1 | const mongoose = require('mongoose')
2 |
3 | const walletSchema = mongoose.Schema(
4 | {
5 | UserId: { type: Number },
6 | keystore: {
7 | version: { type: Number },
8 | id: { type: String },
9 | address: { type: String },
10 | crypto: {
11 | ciphertext: { type: String },
12 | cipherparams: {
13 | iv: { type: String },
14 | },
15 | cipher: { type: String },
16 | kdf: { type: String },
17 | kdfparams: {
18 | dklen: { type: Number },
19 | salt: { type: String },
20 | n: { type: Number },
21 | r: { type: Number },
22 | p: { type: Number },
23 | },
24 | mac: { type: String },
25 | },
26 | },
27 | num: { type: Number },
28 | btc: {
29 | publicKey: { type: String },
30 | addressSegWitCompat: { type: String },
31 | addressSegWit: { type: String },
32 | publicKeySegWit: { type: String },
33 | ek: { type: String },
34 | },
35 | mnemo: { type: String },
36 | tronAddress: { type: String },
37 | tronValue: { type: String },
38 | walletV2: {
39 | keystore: {
40 | version: { type: Number },
41 | id: { type: String },
42 | address: { type: String },
43 | crypto: {
44 | ciphertext: { type: String },
45 | cipherparams: {
46 | iv: { type: String },
47 | },
48 | cipher: { type: String },
49 | kdf: { type: String },
50 | kdfparams: {
51 | dklen: { type: Number },
52 | salt: { type: String },
53 | n: { type: Number },
54 | r: { type: Number },
55 | p: { type: Number },
56 | },
57 | mac: { type: String },
58 | },
59 | },
60 | btc: {
61 | publicKey: { type: String },
62 | addressSegWitCompat: { type: String },
63 | addressSegWit: { type: String },
64 | publicKeySegWit: { type: String },
65 | ek: { type: String },
66 | },
67 | mnemo: { type: String },
68 | tronAddress: { type: String },
69 | tronValue: { type: String },
70 | },
71 | },
72 | {
73 | collection: 'wallet',
74 | }
75 | )
76 |
77 | const Wallet = mongoose.model('wallet', walletSchema)
78 |
79 | module.exports = Wallet
80 |
--------------------------------------------------------------------------------
/manager/notification.js:
--------------------------------------------------------------------------------
1 | const { JWT } = require('google-auth-library')
2 | const serviceAccount = require('../conf/satt-token-firebase-adminsdk-fwxcj-2215bda3fa.json')
3 | const axios = require('axios')
4 |
5 | const getAccessToken = () => {
6 | return new Promise((resolve, reject) => {
7 | let serAccount = serviceAccount
8 | const key = serAccount
9 | const jwtClient = new JWT(
10 | key.client_email,
11 | null,
12 | key.private_key,
13 | ['https://www.googleapis.com/auth/cloud-platform'],
14 | null
15 | )
16 | jwtClient.authorize((err, tokens) => {
17 | if (err) {
18 | reject(err)
19 | return
20 | }
21 | resolve(tokens.access_token)
22 | })
23 | })
24 | }
25 |
26 | exports.sendNotification = async (data) => {
27 | let fireBaseAccessToken = await getAccessToken()
28 | var axiosOptions = {
29 | url: 'https://fcm.googleapis.com/v1/projects/satt-token/messages:send',
30 | method: 'post',
31 | headers: {
32 | 'Content-Type': 'application/json',
33 | Authorization: 'Bearer ' + fireBaseAccessToken,
34 | },
35 | data: JSON.stringify(data),
36 | }
37 | axios(axiosOptions)
38 | .then((response) => {})
39 | .catch((error) => {})
40 | }
41 |
42 | exports.sendNotificationTest = async (req, res) => {
43 | let notification = {
44 | idNode: '0149',
45 | type: 'NotifType',
46 | status: 'done',
47 | label: 'label',
48 | isSeen: false,
49 | isSend: false,
50 | attachedEls: {
51 | id: 149,
52 | },
53 | created: new Date(),
54 | }
55 | //let token="dMhtAVFNRAqSrlHtePzqk_:APA91bFFr8q8j_XBcZDGSnPvrVgSJvD3dxXP6thieH_LqGRb-joMN17fsLEgTDF6mhoXX_hO11wajyDICdGs203RVARUIxOZ8u84g0KjD9umoEeEh5_hDanflpNub1EmnWhZiw1iXGsV";
56 | let token =
57 | 'ckGww57_lZ23aTxajLkzyh:APA91bGaqiJ7ny5CE0Jj6TOFOdiDYjW8UFpzSnHLy3NyPB5YHj6Hc232GodJP1o8ZyXK5Z6v11HVgVKmkmU9AfbJgDPx0v9MDckN'
58 | let data = {
59 | message: {
60 | token,
61 | data: {
62 | obj: JSON.stringify(notification),
63 | },
64 | },
65 | }
66 |
67 | let fireBaseAccessToken = await getAccessToken()
68 | var clientServerOptions = {
69 | url: 'https://fcm.googleapis.com/v1/projects/satt-token/messages:send',
70 | data: JSON.stringify(data),
71 | method: 'POST',
72 | headers: {
73 | 'Content-Type': 'application/json',
74 | Authorization: 'Bearer ' + fireBaseAccessToken,
75 | },
76 | }
77 |
78 | axios(clientServerOptions)
79 | .then((response) => {
80 | res.send(response.data)
81 | })
82 | .catch((error) => {
83 | console.error(error)
84 | })
85 | }
86 |
87 | // module.exports = { sendNotification }
88 |
--------------------------------------------------------------------------------
/contracts/PriceGap.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.5;
2 |
3 | contract owned {
4 | address payable public owner;
5 |
6 | constructor () public {
7 | owner = msg.sender;
8 | }
9 |
10 | modifier onlyOwner {
11 | require(msg.sender == owner);
12 | _;
13 | }
14 |
15 | function transferOwnership(address payable newOwner) onlyOwner public {
16 | owner = newOwner;
17 | }
18 | }
19 |
20 | interface IERC20 {
21 |
22 | function transfer(address _to, uint256 _value) external;
23 | function transferFrom(address _from, address _to, uint256 _value) external returns (bool success);
24 | }
25 |
26 | contract ERC20Holder is owned {
27 |
28 |
29 | function tokenFallback(address _from, uint _value, bytes memory _data) pure public returns (bytes32 hash) {
30 | bytes32 tokenHash = keccak256(abi.encodePacked(_from,_value,_data));
31 | return tokenHash;
32 | }
33 |
34 | function() external payable {}
35 |
36 | function withdraw() onlyOwner public {
37 | owner.transfer(address(this).balance);
38 | }
39 |
40 | function transferToken (address token,address to,uint256 val) public onlyOwner {
41 | IERC20 erc20 = IERC20(token);
42 | erc20.transfer(to,val);
43 | }
44 |
45 | }
46 |
47 |
48 | contract priceGap is ERC20Holder {
49 |
50 | address satt = address(0xDf49C9f599A0A9049D97CFF34D0C30E468987389);
51 | address signer = address(0xb0959d3CAEF1a0526cA6Ca9069994A80B8baffC8);
52 |
53 | mapping (address => bool) paid;
54 |
55 |
56 | constructor () public {
57 | }
58 |
59 | function setSigner (address a) public onlyOwner {
60 | signer = a;
61 | }
62 |
63 | function setSatt (address a) public onlyOwner {
64 | satt = a;
65 | }
66 |
67 | function getGap (address a,uint256 b, uint8 v, bytes32 r, bytes32 s) public {
68 |
69 | require(!paid[a]);
70 | bytes32 h = keccak256(abi.encodePacked("\x19Ethereum Signed Message:\n32", keccak256(abi.encode(a,b))));
71 | require( ecrecover(h, v, r, s) == signer);
72 | IERC20 erc20 = IERC20(satt);
73 |
74 | paid[a] = true;
75 |
76 | uint256 amt = b*1000000000000000000;
77 |
78 | erc20.transfer(a,amt);
79 |
80 | }
81 |
82 | function testhash (address a,uint256 b, uint8 v, bytes32 r, bytes32 s) public view returns (bytes32) {
83 | bytes32 i = keccak256(abi.encodePacked("\x19Ethereum Signed Message:\n32", keccak256(abi.encode(a,b))));
84 |
85 | return i;
86 | }
87 |
88 | function test (address a,uint256 b, uint8 v, bytes32 r, bytes32 s) public view returns (address) {
89 | bytes32 k = keccak256(abi.encodePacked("\x19Ethereum Signed Message:\n32", keccak256(abi.encode(a,b))));
90 | address j = ecrecover(k, v, r, s);
91 |
92 | return j;
93 | }
94 |
95 | }
--------------------------------------------------------------------------------
/model/UserArchive.model.js:
--------------------------------------------------------------------------------
1 | const mongoose = require('mongoose')
2 |
3 | const userArchivedSchema = mongoose.Schema(
4 | {
5 | _id: { type: Number },
6 | first_name: { type: String },
7 | name: { type: String },
8 | idSn: { type: Number },
9 | idOnSn: { type: String },
10 | idOnSn2: { type: String },
11 | idOnSn3: { type: String },
12 | email: { type: String },
13 | username: { type: String },
14 | firstName: { type: String },
15 | lastName: { type: String },
16 | lastLogin: { type: Date },
17 | newsLetter: { type: Boolean },
18 | onBoarding: { type: Boolean },
19 | account_locked: { type: Boolean },
20 | failed_count: { type: Number },
21 | date_locked: { type: Number },
22 | enabled: { type: Number },
23 | locale: { type: String },
24 | userSatt: { type: Boolean },
25 | picLink: { type: String },
26 | dateFirstAttempt: { type: Number },
27 | completed: { type: Boolean },
28 | password: { type: String },
29 | secureCode: {
30 | code: { type: Number },
31 | expiring: { type: Number },
32 | type: { type: String },
33 | },
34 | hasWallet: { type: Boolean },
35 | hasWalletV2: { type: Boolean, default: false },
36 | passphrase: { type: Boolean },
37 | is2FA: { type: Boolean },
38 | secret: { type: String },
39 | photoUpdated: { type: Boolean },
40 | isChanged: { type: Boolean },
41 | birthday: { type: String },
42 | gender: { type: String },
43 | daily: [
44 | {
45 | Date: { type: Number },
46 | Balance: { type: String },
47 | convertDate: { type: String },
48 | },
49 | ],
50 | weekly: [
51 | {
52 | Date: { type: Number },
53 | Balance: { type: String },
54 | convertDate: { type: String },
55 | },
56 | ],
57 | monthly: [
58 | {
59 | Date: { type: Number },
60 | Balance: { type: String },
61 | convertDate: { type: String },
62 | },
63 | ],
64 | address: { type: String },
65 | city: { type: String },
66 | country: { type: String },
67 | zipCode: { type: String },
68 | visitPassphrase: { type: Boolean },
69 | fireBaseAccessToken: { type: String },
70 | phone: {
71 | number: { type: String },
72 | internationalNumber: { type: String },
73 | nationalNumber: { type: String },
74 | e164Number: { type: String },
75 | countryCode: { type: String },
76 | dialCode: { type: String },
77 | },
78 | },
79 | { timestamps: true, strict: false, collection: 'sn_user_archived' }
80 | )
81 | const UserArchived = mongoose.model('sn_user_archived', userArchivedSchema)
82 | module.exports = UserArchived
83 |
--------------------------------------------------------------------------------
/.github/workflows/codeql.yml:
--------------------------------------------------------------------------------
1 | # For most projects, this workflow file will not need changing; you simply need
2 | # to commit it to your repository.
3 | #
4 | # You may wish to alter this file to override the set of languages analyzed,
5 | # or to provide custom queries or build logic.
6 | #
7 | # ******** NOTE ********
8 | # We have attempted to detect the languages in your repository. Please check
9 | # the `language` matrix defined below to confirm you have the correct set of
10 | # supported CodeQL languages.
11 | #
12 | name: "CodeQL"
13 |
14 | on:
15 | push:
16 | branches: [ "develop", mainnet ]
17 | pull_request:
18 | # The branches below must be a subset of the branches above
19 | branches: [ "develop" ]
20 | schedule:
21 | - cron: '33 12 * * 5'
22 |
23 | jobs:
24 | analyze:
25 | name: Analyze
26 | runs-on: ubuntu-latest
27 | permissions:
28 | actions: read
29 | contents: read
30 | security-events: write
31 |
32 | strategy:
33 | fail-fast: false
34 | matrix:
35 | language: [ 'javascript' ]
36 | # CodeQL supports [ 'cpp', 'csharp', 'go', 'java', 'javascript', 'python', 'ruby' ]
37 | # Use only 'java' to analyze code written in Java, Kotlin or both
38 | # Use only 'javascript' to analyze code written in JavaScript, TypeScript or both
39 | # Learn more about CodeQL language support at https://aka.ms/codeql-docs/language-support
40 |
41 | steps:
42 | - name: Checkout repository
43 | uses: actions/checkout@v3
44 |
45 | # Initializes the CodeQL tools for scanning.
46 | - name: Initialize CodeQL
47 | uses: github/codeql-action/init@v2
48 | with:
49 | languages: ${{ matrix.language }}
50 | # If you wish to specify custom queries, you can do so here or in a config file.
51 | # By default, queries listed here will override any specified in a config file.
52 | # Prefix the list here with "+" to use these queries and those in the config file.
53 |
54 | # Details on CodeQL's query packs refer to : https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-code-scanning#using-queries-in-ql-packs
55 | # queries: security-extended,security-and-quality
56 |
57 |
58 | # Autobuild attempts to build any compiled languages (C/C++, C#, Go, or Java).
59 | # If this step fails, then you should remove it and run the build manually (see below)
60 | - name: Autobuild
61 | uses: github/codeql-action/autobuild@v2
62 |
63 | # ℹ️ Command-line programs to run using the OS shell.
64 | # 📚 See https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions#jobsjob_idstepsrun
65 |
66 | # If the Autobuild fails above, remove it and uncomment the following three lines.
67 | # modify them (or add more) to build your code if your project, please refer to the EXAMPLE below for guidance.
68 |
69 | # - run: |
70 | # echo "Run, Build Application using script"
71 | # ./location_of_script_within_repo/buildscript.sh
72 |
73 | - name: Perform CodeQL Analysis
74 | uses: github/codeql-action/analyze@v2
75 | with:
76 | category: "/language:${{matrix.language}}"
77 |
--------------------------------------------------------------------------------
/libs/transfer/readme.md:
--------------------------------------------------------------------------------
1 | # About
2 |
3 | This package act as a transaction signer to sign and send token funds from one account address to another.
4 |
5 | # Installation
6 |
7 | ```
8 | npm i @atayen-org/transfer
9 | ```
10 |
11 | # Methods
12 |
13 | ## transferTokens
14 |
15 | Use this function to transfer native or custom EVM tokens. However you need to provide token's SmartContract address and ABI if you want to transfer custom tokens.
16 |
17 | | Properties | Description |
18 | | ------------------------- | ------------------------------------------------------------------------------------------- |
19 | | fromAddress | Sender address |
20 | | toAddress | Receiver address |
21 | | amount | Amount in wei (make sure it's in wei very important !!) |
22 | | tokenSmartContractAddress | Set to null by default so it will send native tokens |
23 | | tokenSmartContractAbi | Set to null by default |
24 | | provider | You network provider object |
25 | | walletPassword | Your secret encryption account password |
26 | | encryptedPrivateKey | Will be used to decrypt your account along with your encryption password ( walletPasswrod ) |
27 |
28 | ## transferBTC
29 |
30 | For the bitcoin protocol
31 |
32 | | Properties | Description |
33 | | -------------- | ----------------------------------------------- |
34 | | to | the receiver address |
35 | | amount | amount in satochi unit |
36 | | walletPassword | Your secret account password |
37 | | account | account that contain your encrypted btc account |
38 |
39 | # Usage
40 |
41 | ```js
42 | const { transferTokens } = require('@atayen-org/transfer');
43 | const Web3 = require('web3')
44 |
45 | const provider = new Web3.providers.HttpProvider("http_provider_url")
46 | const tokenSmartContractAbi = // you need to provider smart contract abi
47 | const encryptedPrivateKey = // An encrypted version of your private key
48 |
49 | transferTokens({
50 | fromAddress: "0x7ccf8e6b1ea2c018ec133299b4d41de4e5b28304",
51 | toAddress: "0xc8640bc88b5751674e3535ecd398962b69ba9845",
52 | amount: "10000000000000000000",
53 | tokenSmartContractAddress: "0x4CB4473Af06B844d06b5eDeF08983B2C5C61e5af",
54 | tokenSmartContractAbi
55 | provider,
56 | walletPassword: "yourSecretWalletPassword",
57 | encryptedPrivateKey,
58 | }).then((result) => )
59 |
60 | // it will return a promise with the below value
61 | /*
62 |
63 | xX Example values on testnet here Xx
64 | {
65 | blockHash: '0x3e1962d40d9e4d0d44646cf96d4c17159dda6d47eabc6fe24b7ce3c99889c6a4',
66 | blockNumber: 20990200,
67 | transactionHash: '0xe48b9d35688fb83065791a93f05249e31256e04309d884b665bbada537d03c46',
68 | from: '0x7ccf8e6b1ea2c018ec133299b4d41de4e5b28304',
69 | to: '0xc8640bc88b5751674e3535ecd398962b69ba9845',
70 | amount: '10000000000000000000'
71 | }
72 |
73 | */
74 |
75 | ```
76 |
--------------------------------------------------------------------------------
/libs/transfer/transfer-tokens.js:
--------------------------------------------------------------------------------
1 | const Web3 = require('web3')
2 | const Big = require('big.js')
3 | const fromExponential = require('from-exponential')
4 |
5 | module.exports.transferTokens = async function ({
6 | fromAddress,
7 | toAddress,
8 | amount,
9 | tokenSmartContractAddress = null,
10 | tokenSmartContractAbi = null,
11 | provider,
12 | walletPassword,
13 | encryptedPrivateKey,
14 | max = false,
15 | token = false,
16 | network = null,
17 | }) {
18 | const web3 = new Web3(provider)
19 | if (!web3.utils.isAddress(fromAddress)) {
20 | throw Error('The sender address is not a valid ethereum address !!')
21 | }
22 |
23 | if (!web3.utils.isAddress(toAddress)) {
24 | throw Error('The recipient address is not a valid ethereum address !!')
25 | }
26 |
27 | let tokenSmartContract = null
28 |
29 | if (tokenSmartContractAddress !== null) {
30 | tokenSmartContract = new web3.eth.Contract(
31 | tokenSmartContractAbi,
32 | tokenSmartContractAddress
33 | )
34 | }
35 |
36 | const senderBalance =
37 | tokenSmartContractAddress === null
38 | ? await web3.eth.getBalance(fromAddress)
39 | : await tokenSmartContract.methods.balanceOf(fromAddress).call()
40 |
41 | if (new Big(amount).gt(new Big(senderBalance)) && max === 'flase') {
42 | throw Error('No enough balance to perform withdraw !!')
43 | }
44 |
45 | const gasPrice = await web3.eth.getGasPrice()
46 | if (max === 'true') amount = senderBalance
47 |
48 | let gasLimit =
49 | tokenSmartContractAddress === null
50 | ? await web3.eth.estimateGas({ to: toAddress })
51 | : await tokenSmartContract.methods
52 | .transfer(toAddress, amount)
53 | .estimateGas({ from: fromAddress })
54 |
55 | web3.eth.accounts.wallet.decrypt([encryptedPrivateKey], walletPassword)
56 |
57 | try {
58 | let result
59 | if (
60 | tokenSmartContractAddress === null ||
61 | tokenSmartContractAddress === process.env.TOKEN_BTT_CONTRACT
62 | ) {
63 | token && (gasLimit = 21000)
64 | if (max == 'true')
65 | amount = new Big(senderBalance).minus(
66 | new Big(gasLimit).times(new Big(gasPrice))
67 | )
68 |
69 | result = await web3.eth.sendTransaction({
70 | from: fromAddress,
71 | to: toAddress,
72 | value: fromExponential(amount),
73 | gas: gasLimit,
74 | gasPrice,
75 | })
76 | } else {
77 | gasLimit = network === 'BEP20' ? 21000 : 65000
78 | result = await tokenSmartContract.methods
79 | .transfer(toAddress, fromExponential(amount))
80 | .send({
81 | from: fromAddress,
82 | gas: gasLimit,
83 | gasPrice,
84 | })
85 | }
86 |
87 | return {
88 | blockHash: result.blockHash,
89 | blockNumber: result.blockNumber,
90 | transactionHash: result.transactionHash,
91 | from: fromAddress,
92 | to: toAddress,
93 | amount: amount,
94 | }
95 | } catch (error) {
96 | return { error: error.message }
97 | } finally {
98 | web3.eth.accounts.wallet.remove(fromAddress)
99 | }
100 | }
101 |
--------------------------------------------------------------------------------
/conf/fullchain.pem:
--------------------------------------------------------------------------------
1 | -----BEGIN CERTIFICATE-----
2 | MIIFMzCCBBugAwIBAgISBK4Pb3r06tIFL5JD3T/2+GEoMA0GCSqGSIb3DQEBCwUA
3 | MDIxCzAJBgNVBAYTAlVTMRYwFAYDVQQKEw1MZXQncyBFbmNyeXB0MQswCQYDVQQD
4 | EwJSMzAeFw0yMTAxMjQwODEzNTBaFw0yMTA0MjQwODEzNTBaMCExHzAdBgNVBAMT
5 | FndhbGxldC5pZnJhbWUtYXBwcy5jb20wggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAw
6 | ggEKAoIBAQDddRovkVrrL0BXpGEi3LbN/CKBNmyWn5/PF4SNER4FAH/n+HKO6FfH
7 | uB+Y0smOmNlDhYhBku2xOYwnmEYlDh7H/DPkWdJ3GNil5n5mHloLfXSzkanRxlYF
8 | RA8dLSJM1fqVbotQEfuP21u56OxDbYICU7SCFgPl41f7etXP5MxXFtgPTgjVJTaR
9 | bhAPWuwTC0dH0EzpY0HfdB6f8wWwbkvQP6HjMjaH8BWwYAL1jZ1Y6cm9r49qEynI
10 | cr/gnFfkgcgJiaj5uPpZr2sqWm0Teex1aTrzF/aci+Dkdz/d41hnC34jlUB4y4as
11 | pbz4aikfP5jj8sQeVJHjgZwR5Sf7dUfBAgMBAAGjggJSMIICTjAOBgNVHQ8BAf8E
12 | BAMCBaAwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMAwGA1UdEwEB/wQC
13 | MAAwHQYDVR0OBBYEFNsU5fxGivFbV9QlBk6M4dzu0g+AMB8GA1UdIwQYMBaAFBQu
14 | sxe3WFbLrlAJQOYfr52LFMLGMFUGCCsGAQUFBwEBBEkwRzAhBggrBgEFBQcwAYYV
15 | aHR0cDovL3IzLm8ubGVuY3Iub3JnMCIGCCsGAQUFBzAChhZodHRwOi8vcjMuaS5s
16 | ZW5jci5vcmcvMCEGA1UdEQQaMBiCFndhbGxldC5pZnJhbWUtYXBwcy5jb20wTAYD
17 | VR0gBEUwQzAIBgZngQwBAgEwNwYLKwYBBAGC3xMBAQEwKDAmBggrBgEFBQcCARYa
18 | aHR0cDovL2Nwcy5sZXRzZW5jcnlwdC5vcmcwggEFBgorBgEEAdZ5AgQCBIH2BIHz
19 | APEAdgBc3EOS/uarRUSxXprUVuYQN/vV+kfcoXOUsl7m9scOygAAAXczq8NGAAAE
20 | AwBHMEUCIQCANdfxwn2mkxRilTdVThw8cKdwzsn2tiEpa7s5Bwmq0wIgdCueSgf8
21 | rW9UkPl5KdwzdvhYAP3Bb4lzywbaQvnGPm0AdwD2XJQv0XcwIhRUGAgwlFaO400T
22 | GTO/3wwvIAvMTvFk4wAAAXczq8M6AAAEAwBIMEYCIQCatfWTjBc83uDE2+d3yQOK
23 | CnEJoIJ6+imH8KlXj5/c7gIhAPZgu7KLe7j1tFiOrr7Y28oZ94QaWrTLGrRf3JdQ
24 | ymxqMA0GCSqGSIb3DQEBCwUAA4IBAQAXQBX+UEqwWwGwoJ9u39dHZEgnyejXEnzZ
25 | D7oAym4awIP+CMfKq9peTeG5wI9vBPviSBOymrr/MXcaMJKbUP5JU1nY3aN3dmzz
26 | AJ9d+VHbe5VtJNd/+5WWpXOf2YHHWmyCFDJbJfp4qMbubra/AUbVLEDGuZsCrTTK
27 | R654NOlSJmKFtvV1aLNpwfT3XDAfIG2Y5OjIjgmtpMx1cONQl42sizIJAHb9TYjt
28 | bteQmkI5IgjHmqR2aUHTN21hkgnoyblgH9DZCZE82QWUZAMyf1yRzCX1GN/Nfs6l
29 | BzaGxvsCCl235lj73cQV0TSuoZy2jAjRrtQxvX5Jm3L+GUBbAKGN
30 | -----END CERTIFICATE-----
31 | -----BEGIN CERTIFICATE-----
32 | MIIEZTCCA02gAwIBAgIQQAF1BIMUpMghjISpDBbN3zANBgkqhkiG9w0BAQsFADA/
33 | MSQwIgYDVQQKExtEaWdpdGFsIFNpZ25hdHVyZSBUcnVzdCBDby4xFzAVBgNVBAMT
34 | DkRTVCBSb290IENBIFgzMB4XDTIwMTAwNzE5MjE0MFoXDTIxMDkyOTE5MjE0MFow
35 | MjELMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUxldCdzIEVuY3J5cHQxCzAJBgNVBAMT
36 | AlIzMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAuwIVKMz2oJTTDxLs
37 | jVWSw/iC8ZmmekKIp10mqrUrucVMsa+Oa/l1yKPXD0eUFFU1V4yeqKI5GfWCPEKp
38 | Tm71O8Mu243AsFzzWTjn7c9p8FoLG77AlCQlh/o3cbMT5xys4Zvv2+Q7RVJFlqnB
39 | U840yFLuta7tj95gcOKlVKu2bQ6XpUA0ayvTvGbrZjR8+muLj1cpmfgwF126cm/7
40 | gcWt0oZYPRfH5wm78Sv3htzB2nFd1EbjzK0lwYi8YGd1ZrPxGPeiXOZT/zqItkel
41 | /xMY6pgJdz+dU/nPAeX1pnAXFK9jpP+Zs5Od3FOnBv5IhR2haa4ldbsTzFID9e1R
42 | oYvbFQIDAQABo4IBaDCCAWQwEgYDVR0TAQH/BAgwBgEB/wIBADAOBgNVHQ8BAf8E
43 | BAMCAYYwSwYIKwYBBQUHAQEEPzA9MDsGCCsGAQUFBzAChi9odHRwOi8vYXBwcy5p
44 | ZGVudHJ1c3QuY29tL3Jvb3RzL2RzdHJvb3RjYXgzLnA3YzAfBgNVHSMEGDAWgBTE
45 | p7Gkeyxx+tvhS5B1/8QVYIWJEDBUBgNVHSAETTBLMAgGBmeBDAECATA/BgsrBgEE
46 | AYLfEwEBATAwMC4GCCsGAQUFBwIBFiJodHRwOi8vY3BzLnJvb3QteDEubGV0c2Vu
47 | Y3J5cHQub3JnMDwGA1UdHwQ1MDMwMaAvoC2GK2h0dHA6Ly9jcmwuaWRlbnRydXN0
48 | LmNvbS9EU1RST09UQ0FYM0NSTC5jcmwwHQYDVR0OBBYEFBQusxe3WFbLrlAJQOYf
49 | r52LFMLGMB0GA1UdJQQWMBQGCCsGAQUFBwMBBggrBgEFBQcDAjANBgkqhkiG9w0B
50 | AQsFAAOCAQEA2UzgyfWEiDcx27sT4rP8i2tiEmxYt0l+PAK3qB8oYevO4C5z70kH
51 | ejWEHx2taPDY/laBL21/WKZuNTYQHHPD5b1tXgHXbnL7KqC401dk5VvCadTQsvd8
52 | S8MXjohyc9z9/G2948kLjmE6Flh9dDYrVYA9x2O+hEPGOaEOa1eePynBgPayvUfL
53 | qjBstzLhWVQLGAkXXmNs+5ZnPBxzDJOLxhF2JIbeQAcH5H0tZrUlo5ZYyOqA7s9p
54 | O5b85o3AM/OJ+CktFBQtfvBhcJVd9wvlwPsk+uyOy2HI7mNxKKgsBTt375teA2Tw
55 | UdHkhVNcsAKX1H7GNNLOEADksd86wuoXvg==
56 | -----END CERTIFICATE-----
57 |
--------------------------------------------------------------------------------
/public/tron-icon.svg:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
--------------------------------------------------------------------------------
/contracts/SattResolver.sol:
--------------------------------------------------------------------------------
1 | pragma solidity ^0.5;
2 |
3 | contract owned {
4 | address payable public owner;
5 |
6 | constructor () public {
7 | owner = msg.sender;
8 | }
9 |
10 | modifier onlyOwner {
11 | require(msg.sender == owner);
12 | _;
13 | }
14 |
15 | function transferOwnership(address payable newOwner) onlyOwner public {
16 | owner = newOwner;
17 | }
18 | }
19 |
20 | contract SattResolver is owned {
21 |
22 | struct PublicKey {
23 | bytes32 x;
24 | bytes32 y;
25 | }
26 |
27 | mapping(bytes32=>address) addresses;
28 | mapping(bytes32=>string) names;
29 | mapping(bytes32=>mapping(uint256=>bytes)) abis;
30 | mapping(bytes32=>bytes) hashes;
31 | mapping(bytes32=>PublicKey) pubkeys;
32 | mapping(bytes32=>mapping(string=>string)) texts;
33 |
34 | event AddrChanged(bytes32 indexed node, address a);
35 | event NameChanged(bytes32 indexed node, string name);
36 | event ContenthashChanged(bytes32 indexed node, bytes hash);
37 | event ABIChanged(bytes32 indexed node, uint256 indexed contentType);
38 | event PubkeyChanged(bytes32 indexed node, bytes32 x, bytes32 y);
39 | event TextChanged(bytes32 indexed node, string indexedKey, string key);
40 |
41 | function supportsInterface(bytes4 interfaceID) public pure returns (bool) {
42 | return interfaceID == 0x3b3b57de || interfaceID == 0x01ffc9a7 || interfaceID == 0x691f3431 || interfaceID == 0x2203ab56 || interfaceID == 0xc8690233 || interfaceID == 0x59d1d43c || interfaceID == 0xbc1c58d1;
43 | }
44 |
45 | function addr(bytes32 node) external view returns (address)
46 | {
47 | return addresses[node];
48 | }
49 |
50 | function setAddr(bytes32 node, address ad) external onlyOwner {
51 | addresses[node] = ad;
52 | emit AddrChanged(node, ad);
53 | }
54 |
55 | function name(bytes32 node) external view returns (string memory) {
56 | return names[node];
57 | }
58 |
59 | function setName(bytes32 node, string calldata nme) external onlyOwner {
60 | emit NameChanged(node, nme);
61 | }
62 |
63 | function contenthash(bytes32 node) external view returns (bytes memory) {
64 | return hashes[node];
65 | }
66 |
67 | function setContenthash(bytes32 node, bytes calldata hash) external onlyOwner {
68 | hashes[node] = hash;
69 | emit ContenthashChanged(node, hash);
70 | }
71 |
72 | function ABI(bytes32 node, uint256 contentTypes) external view returns (uint256, bytes memory) {
73 | mapping(uint256=>bytes) storage abiset = abis[node];
74 |
75 | for (uint256 contentType = 1; contentType <= contentTypes; contentType <<= 1) {
76 | if ((contentType & contentTypes) != 0 && abiset[contentType].length > 0) {
77 | return (contentType, abiset[contentType]);
78 | }
79 | }
80 |
81 | return (0, bytes(""));
82 | }
83 |
84 | function setABI(bytes32 node, uint256 contentType, bytes calldata data) external onlyOwner {
85 | require(((contentType - 1) & contentType) == 0);
86 |
87 | abis[node][contentType] = data;
88 | emit ABIChanged(node, contentType);
89 | }
90 |
91 | function pubkey(bytes32 node) external view returns (bytes32 x, bytes32 y) {
92 | return (pubkeys[node].x, pubkeys[node].y);
93 | }
94 |
95 | function setPubkey(bytes32 node, bytes32 x, bytes32 y) external onlyOwner {
96 | pubkeys[node] = PublicKey(x, y);
97 | emit PubkeyChanged(node, x, y);
98 | }
99 |
100 | function text(bytes32 node, string calldata key) external view returns (string memory) {
101 | return texts[node][key];
102 | }
103 |
104 | function setText(bytes32 node, string calldata key, string calldata value) external onlyOwner {
105 | texts[node][key] = value;
106 | emit TextChanged(node, key, key);
107 | }
108 | }
--------------------------------------------------------------------------------
/model/user.model.js:
--------------------------------------------------------------------------------
1 | const mongoose = require('mongoose')
2 |
3 | autoIncrement = require('mongoose-auto-increment')
4 | const { mongoConnection } = require('../conf/config')
5 |
6 | const db = mongoose.createConnection(mongoConnection(), {
7 | useNewUrlParser: true,
8 | useUnifiedTopology: true,
9 | useCreateIndex: true,
10 | useFindAndModify: false,
11 | })
12 | autoIncrement.initialize(db)
13 | const userSchema = mongoose.Schema(
14 | {
15 | first_name: { type: String },
16 | name: { type: String },
17 | idSn: { type: Number, default: 0 },
18 | idOnSn: { type: String },
19 | idOnSn2: { type: String },
20 | idOnSn3: { type: String },
21 | created: { type: Date, default: Date.now },
22 | email: { type: String, unique: true },
23 | username: { type: String },
24 | firstName: { type: String },
25 | lastName: { type: String },
26 | lastLogin: { type: Date, default: Date.now },
27 | newsLetter: { type: Boolean },
28 | onBoarding: { type: Boolean, default: false },
29 | account_locked: { type: Boolean, default: 0 },
30 | failed_count: { type: Number, default: 0 },
31 | date_locked: { type: Number },
32 | enabled: { type: Number },
33 | locale: { type: String, default: 'en' },
34 | userSatt: { type: Boolean, default: true },
35 | picLink: { type: String },
36 | dateFirstAttempt: { type: Number },
37 | completed: { type: Boolean, default: false },
38 | password: { type: String },
39 | lastHarvestDate: { type: mongoose.Schema.Types.Mixed },
40 |
41 | secureCode: {
42 | code: { type: Number },
43 | expiring: { type: Number },
44 | type: { type: String },
45 | attempts: { type: Number, default: 0 },
46 | lastTry: { type: Number },
47 | },
48 | newEmail: {
49 | email: { type: String },
50 | expiring: { type: Number },
51 | code: { type: Number },
52 | },
53 | hasWallet: { type: Boolean, default: false },
54 | hasWalletV2: { type: Boolean, default: false },
55 | migrated:{ type: Boolean, default: false },
56 | passphrase: { type: Boolean, default: false },
57 | is2FA: { type: Boolean, default: false },
58 | hasBiometrics: { type: Boolean, default: false },
59 | secret: { type: String },
60 | photoUpdated: { type: Boolean, default: false },
61 | isChanged: { type: Boolean, default: false },
62 | birthday: { type: String },
63 | gender: { type: String },
64 | daily: [
65 | {
66 | Date: { type: Number },
67 | Balance: { type: String },
68 | convertDate: { type: String },
69 | },
70 | ],
71 | weekly: [
72 | {
73 | Date: { type: Number },
74 | Balance: { type: String },
75 | convertDate: { type: String },
76 | },
77 | ],
78 | monthly: [
79 | {
80 | Date: { type: Number },
81 | Balance: { type: String },
82 | convertDate: { type: String },
83 | },
84 | ],
85 | address: { type: String },
86 | city: { type: String },
87 | country: { type: String },
88 | zipCode: { type: String },
89 | visitPassphrase: { type: Boolean, default: false },
90 | fireBaseAccessToken: { type: String },
91 | fireBaseAccessTokenMObile: { type: String },
92 |
93 | phone: {
94 | number: { type: String },
95 | internationalNumber: { type: String },
96 | nationalNumber: { type: String },
97 | e164Number: { type: String },
98 | countryCode: { type: String },
99 | dialCode: { type: String },
100 | },
101 | },
102 | { timestamps: true, strict: false, collection: 'user' }
103 | )
104 | userSchema.plugin(autoIncrement.plugin, {
105 | model: 'user',
106 | field: '_id',
107 | startAt: 100,
108 | incrementBy: 1,
109 | })
110 | const User = db.model('user', userSchema)
111 | module.exports = User
112 |
--------------------------------------------------------------------------------
/public/locales/en.json:
--------------------------------------------------------------------------------
1 | {
2 | "welcome": "Welcome !",
3 | "finished_inscription": "Your registration is almost complete! You just have to validate your email to access all the services offered by SaTT.",
4 | "validate_mail": "I confirm my email",
5 | "contact_support": "If you did not initiate this registration, please contact the technical support.",
6 | "create_portfolio": "Say ‘hello’ to your new wallet",
7 | "create_secure": "Create an easily accessible and secure wallet Select a strong password that you’ll remember Of note, we are unable to help recover lost passwords.",
8 | "monetisez": "Monetization made easy",
9 | "monetisez_description": "Whether you’re new to the social media landscape or are an established influencer, your audience size translates directly into your earnings. The SaTT platform leverages blockchain to automate your payments with uncompromising accuracy, every time.",
10 | "automate_campaign": " Ad Pool Revolution, a new and easy way to promote brands",
11 | "automate_campaign_description": "Anyone can quickly create an Advertising Pool and allow influencers from all over the world to promote their brands. Set the appropriate budget without a middleman for a much cheaper price and ensure that you’re getting the most bang for your buck.",
12 | "questions": "Questions ? Ask away!",
13 | "questions_description": "We’re here to support you! Our dedicated support staff is always within reach via our social platforms. Let’s find answers, together. ",
14 | "consult_faq": "Consult the FAQ",
15 | "reset_pass 1": "Reset your login password",
16 | "new_pass": "New password",
17 | "ask_pass": "You asked to reset your login password",
18 | "connex": "to dapp.satt.com",
19 | "valid_mess": "Your link for the ",
20 | "reject_trans": "Unfortunately, the advertiser rejected your",
21 | "link_w": "link.",
22 | "link_added": "New link alert ! 🎉",
23 | "valid_contact": "contact us",
24 | "reject_questions": "Questions ! Don't be shy ! we're here to help.",
25 | "reject_reason": "Here’s what they said...",
26 | "reject_link": "Rejected link 😧",
27 | "valid_need": "If you have any question",
28 | "valid_wish": "From our SaTT family to yours, we wish you all the best !",
29 | "valid_accepted": "campaign link was just validated by the advertiser. It’s high time to celebrate !",
30 | "reject_cmp": "campaign has been rejected by the advertiser.",
31 | "valid_question": "Ready to collect your earnings ?",
32 | "valid_gaz": "Your hard-earned SaTT is ready for you to claim. At the same time, don’t forget thatyou need to verify if you have Ethereum or Binance Coin in your wallet. In order to interface with the blockchain, you need to verify this first.",
33 | "valid_post": "Get posting !",
34 | "link": "Click on the link below to reset it",
35 | "reset_pass2": "Reset your password",
36 | "reset_pass3": "If you did not make this request, ignore this Email",
37 | "contact": "Contact us",
38 | "about": "About SaTT",
39 | "insert-question": "Questions or concerns? We’re just a message away!",
40 | "new_link": "Say ‘hello’ to your campaign’s newest link :",
41 | "new_link_added": "has been added",
42 | "new_link_campaign": "The world is your oyster.",
43 | "Hello": "Hello",
44 | "link_valid": "Congratulations ! 🍾",
45 | "link_trans": "Your",
46 | "Bonjour": "Bonjour",
47 | "ask_to_send": "is requesting",
48 | "here_is_message": "message to you",
49 | "here_is_the_message": "Here is the message:",
50 | "wallet_of": "wallet is",
51 | "is": "is",
52 | "cmp_link": "cmp_link",
53 | "Support": "Contact customer service.",
54 | "cmp_title": "cmp_title",
55 | "changement_email_presque_terminé": "You’re just steps away from changing your email address...",
56 | "validation_code": "Your verification code is :",
57 | "code-expire": "Please submit your code within the next 5 minutes. Afterward, the code will be void.",
58 | "code-request": "Didn’t request to change your email ?",
59 | "time-request": "Request time",
60 | "Location": "Location",
61 | "request-done": "has been requested.",
62 | "request": "A request to reset your",
63 | "mail": "E-mail adress",
64 | "verif-code": "Email reset request",
65 | "send-money": "Fulfill request"
66 | }
67 |
--------------------------------------------------------------------------------
/public/locales/fr.json:
--------------------------------------------------------------------------------
1 | {
2 | "welcome": "bienvenue !",
3 | "finished_inscription": "Votre inscription est presque terminée ! Il ne vous reste plus qu’à valider votre mail pour accéder à tous les services proposés par SaTT. ",
4 | "validate_mail": "Je valide mon mail",
5 | "contact_support": "Si vous n'êtes pas à l'origine de cette inscription, veuillez contacter le support.",
6 | "create_portfolio": "Créer votre portefeuille !",
7 | "create_secure": "Créez et sécurisez votre portefeuille ! Choisissez et notez vos mots de passe avec précaution. Nous ne pouvons pas vous aider à le retrouver en cas de perte.",
8 | "monetisez": "Monétisez votre audience !",
9 | "monetisez_description": "Que vous ayez 50 abonnés ou 1 million de followers, soyez rémunéré à la hauteur de votre audience. La plateforme Satturn est conçue dans le but de convenir au plus grand nombre. Grâce à la blockchain, soyez sûr d’être rémunéré, tout est automatisé.",
10 | "automate_campaign": "Concevez, paramétrez, automatisez votre campagne. ",
11 | "automate_campaign_description": "Choisissez parmi les influencers du monde entier, les petits ou les plus grands.Planifiez votre budget sans intermédiaire ni négociation. Ayez le contrôle sur votre campagne, faites en un chef-d'œuvre à votre image.Étudiez vos statistiques et recommencez. Profitez de frais compétitifs. Vous avez toutes les clés en main pour faire de votre campagne un succès !",
12 | "questions": "Vous avez des questions ?",
13 | "questions_description": "Toute notre équipe support est disponible pour répondre à chacune de vos questions. N'hésitez pas à les contacter via nos différents réseaux sociaux !",
14 | "consult_faq": "Consultez la FAQ",
15 | "reset_pass1": "",
16 | "ask_pass": "Vous avez demandé à renouveler votre mot de passe",
17 | "connex": "de connexion au site dapp.satt.com.",
18 | "link": "Cliquez sur le lien ci-dessous pour réinitialiser votre nouveau mot de passe de connexion",
19 | "reset_pass2": "Réinitialiser le mot de passe",
20 | "reset_pass3": "Si vous n'êtes pas à l'origine de cette demande, veuillez ignorez cet Email",
21 | "link_w": "lien.",
22 | "contact": "Nous contacter",
23 | "link_added": "Alerte nouveau lien ! 🎉",
24 | "insert-question": "Questions ou préoccupations? Nous ne sommes qu'à un message !",
25 | "reject_questions": "Des questions ! Ne soyez pas timide ! nous sommes là pour vous aider.",
26 | "reject_reason": "Voici ce qu'ils ont dit...",
27 | "reject_link": "Lien rejeté...",
28 | "valid_mess": "Votre lien pour la campagne",
29 | "new_link": "Dites « bonjour » au dernier lien de votre campagne :",
30 | "new_link_campaign": "Le monde est ton coquillage.",
31 | "new_link_added": "a été ajouté",
32 | "reject_cmp": "a été rejeté par l'annonceur !",
33 | "valid_accepted": "le lien de campagne vient d'être validé par l'annonceur. Il est grand temps de célébrer !",
34 | "valid_question": "Prêt à récolter vos gains ?",
35 | "valid_contact": "nous contactez",
36 | "valid_wish": "De la part de notre famille SaTT à la vôtre, nous vous souhaitons tout le meilleur !",
37 | "valid_need": "En cas de question, n'hésitez pas à",
38 | "valid_gaz": "vous pouvez récolter vos gains à tout moment, mais n'oubliez pas que chaque transaction coûte du gaz ! Pensez à vérifier que vous possédez des Ethereum (ERC20 et/ou) des Binance Coin(BEP20)",
39 | "about": "À propos de SaTT",
40 | "valid_post": "Poster un autre lien",
41 | "Hello": "Bonjour",
42 | "reject_trans": "Malheureusement, l'annonceur a rejeté votre",
43 | "link_valid": "Lien Validé ! 🍾",
44 | "link_trans": "Votre",
45 | "Bonjour": "Bonjour",
46 | "new_pass": "Nouveau password",
47 | "ask_to_send": "Vous demande de lui envoyer",
48 | "here_is_message": "Voici son message",
49 | "wallet_of": "la portefeuille de",
50 | "is": "est",
51 | "changement_email_presque_terminé": "Votre demande de changement d'adresse email est presque terminée !",
52 | "validation_code": "Votre code de validation",
53 | "code-expire": "Ce code de vérification ne sera valable que 5 minutes",
54 | "code-request": "Vous n'avez pas demandé de modifier votre email ?",
55 | "Support": "Contactez le support.",
56 | "time-request": "Moment de la requête",
57 | "Location": "Localisation",
58 | "request-done": "a été faite.",
59 | "request": "Une demande de réinitialisation de votre",
60 | "mail": "adresse Mail",
61 | "verif-code": "Code de vérification",
62 | "send-money": "Envoyer la somme"
63 | }
64 |
--------------------------------------------------------------------------------
/routes/external.routes.js:
--------------------------------------------------------------------------------
1 | const express = require('express')
2 | const router = express.Router()
3 |
4 | const {
5 | createUserFromExternalWallet,
6 | externalSocialAccounts,
7 | externalDeleteTiktokChannel,
8 | externalDeleteTiktokChannels,
9 | externalDeleteGoogleChannel,
10 | externalDeleteGoogleChannels,
11 | externalDeleteFacebookChannels,
12 | externalDeleteFacebookChannel,
13 | externalDeleteLinkedinChannels,
14 | externalDeleteLinkedinChannel,
15 | externalDeleteTwitterChannels,
16 | externalDeleteTwitterChannel,
17 | externalVerifyLink,
18 | externalSaveCampaign,
19 | externalVerifyExpiredToken,
20 | externalAccount,
21 | externalUploadPictureToIPFS,
22 | campaignsPictureUploadExternal,
23 | externalAddKits,
24 | uploadExternal,
25 | externalGetLinks,
26 | externalGetOneLinks,
27 | externalApply,
28 | checkHarvest,
29 | externalAnswer,
30 | externalGains,
31 | campaigns,
32 | getBalanceUserExternal,
33 | externalDeleteDraft,
34 | } = require('../controllers/external.controller')
35 | const { verifyAuthExternal } = require('../middleware/passport.middleware')
36 | const {
37 | verifySignatureMiddleware,
38 | idCheckValidation,
39 | addKitsValidation,
40 | externalGainsValidation,
41 | } = require('./../middleware/verifySignature.middleware')
42 | const multer = require('multer')
43 |
44 | const storage = multer.diskStorage({
45 | destination: function (req, file, cb) {
46 | cb(null, 'uploads/') // Uploads directory
47 | },
48 | filename: function (req, file, cb) {
49 | cb(null, Date.now() + '-' + file.originalname)
50 | },
51 | })
52 | const upload = multer({ storage: storage })
53 |
54 | router.post('/create-user', createUserFromExternalWallet)
55 | router.get('/campaigns', campaigns)
56 | router.post('/getBalance', getBalanceUserExternal)
57 | router.post('/createCampaign', verifyAuthExternal, externalSaveCampaign)
58 | // DONE
59 | router.get('/socialAccounts', verifyAuthExternal, externalSocialAccounts)
60 | router.post(
61 | '/campaign/filterLinksExternal',
62 | verifyAuthExternal,
63 | externalGetLinks
64 | )
65 |
66 | router.delete(
67 | '/deleteDraft/:id',
68 | verifyAuthExternal,
69 | idCheckValidation,
70 | externalDeleteDraft
71 | )
72 | router.post(
73 | '/campaign/getLinksExternal',
74 | verifyAuthExternal,
75 | externalGetOneLinks
76 | )
77 |
78 | // DONE
79 |
80 | router.get('/verify-token', verifyAuthExternal, externalVerifyExpiredToken)
81 | router.get('/externalAccount', verifyAuthExternal, externalAccount)
82 |
83 | // DONE
84 | router.delete(
85 | '/RemoveTiktokChannel/:id',
86 | verifyAuthExternal,
87 | externalDeleteTiktokChannel
88 | )
89 |
90 | router.delete(
91 | '/RemoveTiktokChannels',
92 | verifyAuthExternal,
93 | externalDeleteTiktokChannels
94 | )
95 |
96 | router.delete(
97 | '/RemoveGoogleChannel/:id',
98 | verifyAuthExternal,
99 | externalDeleteGoogleChannel
100 | )
101 |
102 | router.delete(
103 | '/RemoveGoogleChannels',
104 | verifyAuthExternal,
105 | externalDeleteGoogleChannels
106 | )
107 |
108 | router.delete(
109 | '/RemoveFacebookChannels',
110 | verifyAuthExternal,
111 | externalDeleteFacebookChannels
112 | )
113 |
114 | router.delete(
115 | '/RemoveFacebookChannel/:id',
116 | verifyAuthExternal,
117 | externalDeleteFacebookChannel
118 | )
119 |
120 | router.delete(
121 | '/RemoveLinkedInChannels',
122 | verifyAuthExternal,
123 | externalDeleteLinkedinChannels
124 | )
125 |
126 | router.delete(
127 | '/remove/:linkedinId/linkedInChannel/:organization',
128 | verifyAuthExternal,
129 | externalDeleteLinkedinChannel
130 | )
131 |
132 | router.delete(
133 | '/RemoveTwitterChannels',
134 | verifyAuthExternal,
135 | externalDeleteTwitterChannels
136 | )
137 |
138 | router.delete(
139 | '/RemoveTwitterChannel/:id',
140 | verifyAuthExternal,
141 | externalDeleteTwitterChannel
142 | )
143 |
144 | router.get(
145 | '/link/verify/:typeSN/:idUser/:idPost',
146 | verifyAuthExternal,
147 | externalVerifyLink
148 | )
149 |
150 | router.post(
151 | '/externalUploadPictureToIPFS/:id',
152 | idCheckValidation,
153 | campaignsPictureUploadExternal,
154 | externalUploadPictureToIPFS
155 | )
156 |
157 | router.post(
158 | '/externalAddKits',
159 | addKitsValidation,
160 | upload.single('file'),
161 | externalAddKits
162 | )
163 |
164 | router.post('/apply', verifyAuthExternal, externalApply)
165 |
166 | router.post('/checkHarvest', verifyAuthExternal, checkHarvest)
167 |
168 | router.post('/externalAnswer', verifyAuthExternal, externalAnswer)
169 | router.post('/externalGains', verifyAuthExternal, externalGains)
170 |
171 | module.exports = router
172 |
--------------------------------------------------------------------------------
/middleware/authValidator.middleware.js:
--------------------------------------------------------------------------------
1 | const Joi = require('joi');
2 |
3 |
4 | /**********
5 | *
6 | * SCHEMA FOR JOI
7 | *
8 | * ********************** */
9 |
10 | // VALIDATION TRANSACTION PASSWORD
11 | const validatePassword = () => Joi.string().min(8).required().custom((value) => {
12 | const RegUpperCase = RegExp('[A-Z]');
13 | const RegLowerCase = RegExp('[a-z]');
14 | const RegNumber = RegExp('[0-9]');
15 | const RegSpecialChar = RegExp('[^A-Za-z0-9]');
16 | if(RegUpperCase.test(value) && RegLowerCase.test(value) && RegNumber.test(value) && RegSpecialChar.test(value)) {
17 | return value;
18 | } else throw Error('password not match')
19 | });
20 |
21 |
22 | // VALIDATION EMAIL
23 | const validateEmail = () => Joi.string().email({ tlds: { allow: false } }).regex(/^[^@]+@[^@]+\.[^@]+$/).required()
24 |
25 |
26 |
27 |
28 |
29 | // SCHEMAS OBJECT
30 | const schemas = {
31 | purgeAccountSchema: Joi.object({
32 | password: validatePassword(),
33 | reason: Joi.string()
34 | }),
35 |
36 | changePasswordSchema: Joi.object({
37 | newpass: validatePassword(),
38 | oldpass: validatePassword()
39 | }),
40 |
41 | emailConnectionSchema: Joi.object({
42 | username: validateEmail(),
43 | password: validatePassword()
44 | }),
45 |
46 | codeRecoverSchema: Joi.object({
47 | mail: validateEmail(),
48 | lang: Joi.string()
49 | }),
50 |
51 | confirmCodeSchema: Joi.object({
52 | code: Joi.number().required(),
53 | email: validateEmail(),
54 | type: Joi.string().required().custom((value) => {
55 | if(value === "reset" || value === "validation") return value;
56 | else throw Error("Type must be 'reset'")
57 | })
58 | }),
59 |
60 | passRecoverSchema: Joi.object({
61 | newpass: validatePassword(),
62 | email: validateEmail(),
63 | code: Joi.number().required()
64 | }),
65 |
66 | emailSignupSchema: Joi.object({
67 | password: validatePassword(),
68 | username: validateEmail(),
69 | lang: Joi.string(),
70 | newsLetter: Joi.boolean()
71 | }),
72 |
73 | resendConfirmationTokenSchema: Joi.object({
74 | email: validateEmail(),
75 | lang: Joi.string()
76 | }),
77 |
78 | authAppleSchema: Joi.object({
79 | id_apple: Joi.string().required(),
80 | mail: Joi.string().email({ tlds: { allow: false } }).regex(/^[^@]+@[^@]+\.[^@]+$/),
81 | idSN: Joi.number().required(),
82 | name: Joi.string()
83 | }),
84 |
85 | logoutSchema: Joi.object({
86 | idUser: Joi.number().required(),
87 | }),
88 |
89 | setVisitSignUpStepSchema: Joi.object({
90 | userId: Joi.number().required(),
91 | visitedStep: Joi.string().required()
92 | }),
93 |
94 | socialdisconnectSchema: Joi.object({
95 | social: Joi.string().required(),
96 | }),
97 |
98 | saveFirebaseAccessTokenSchema: Joi.object({
99 | fb_accesstoken: Joi.string().required()
100 | }),
101 |
102 | updateLastStepSchema: Joi.object({
103 | completed: Joi.boolean().required(),
104 | email: validateEmail(),
105 | firstName: Joi.string(),
106 | lastName: Joi.string()
107 | }),
108 |
109 | verifyQrCodeSchema: Joi.object({
110 | code: Joi.string().required(),
111 | })
112 | }
113 |
114 |
115 |
116 |
117 |
118 | /**********
119 | *
120 | * MIDDLEWARE VALIDATION
121 | *
122 | * ********************** */
123 |
124 |
125 | // MIDDLEWARE FUNCTION
126 | const validationMiddleware = (schema, property) => (req, res, next) => {
127 | const {error} = schema.validate(req[property]);
128 | if(error) throw Error(error);
129 | else next();
130 | }
131 |
132 |
133 |
134 |
135 |
136 | module.exports = {
137 | purgeAccountValidation: validationMiddleware(schemas.purgeAccountSchema, 'body'),
138 | changePasswordValidation: validationMiddleware(schemas.changePasswordSchema, 'body'),
139 | emailConnectionValidation: validationMiddleware(schemas.emailConnectionSchema, 'body'),
140 | codeRecoverValidation: validationMiddleware(schemas.codeRecoverSchema, 'body'),
141 | confirmCodeValidation: validationMiddleware(schemas.confirmCodeSchema, 'body'),
142 | passRecovervalidation: validationMiddleware(schemas.passRecoverSchema, 'body'),
143 | emailSignupValidation: validationMiddleware(schemas.emailSignupSchema, 'body'),
144 | resendConfirmationTokenValidation: validationMiddleware(schemas.resendConfirmationTokenSchema, 'body'),
145 | authAppleValidation: validationMiddleware(schemas.authAppleSchema, 'body'),
146 | logoutValidation: validationMiddleware(schemas.logoutSchema, 'params'),
147 | setVisitSignUpStepValidation: validationMiddleware(schemas.setVisitSignUpStepSchema, 'body'),
148 | socialdisconnectValidation: validationMiddleware(schemas.socialdisconnectSchema, 'params'),
149 | saveFirebaseAccessTokenValidation: validationMiddleware(schemas.saveFirebaseAccessTokenSchema, 'body'),
150 | updateLastStepValidation: validationMiddleware(schemas.updateLastStepSchema, 'body'),
151 | verifyQrCodeValidation: validationMiddleware(schemas.verifyQrCodeSchema, 'body')
152 | };
--------------------------------------------------------------------------------
/manager/accounts.js:
--------------------------------------------------------------------------------
1 | const { Notification, User } = require('../model/index')
2 |
3 | const { sendNotification } = require('./notification')
4 |
5 | const { Tokens } = require('../conf/config')
6 |
7 | exports.notificationManager = async (id, NotifType, label) => {
8 | try {
9 | let notification = {
10 | idNode: '0' + id,
11 | type: NotifType,
12 | status: 'done',
13 | label,
14 | isSeen: false,
15 | isSend: false,
16 | attachedEls: {
17 | id: id,
18 | },
19 | created: new Date(),
20 | }
21 |
22 | const notif = await Notification.create(notification)
23 | let user = await User.findOne({ _id: +id }).select(
24 | 'fireBaseAccessToken '
25 | )
26 | if (user.fireBaseAccessToken) {
27 | let data = {
28 | message: {
29 | token: user.fireBaseAccessToken,
30 | data: {
31 | obj: JSON.stringify(notification),
32 | },
33 | },
34 | }
35 | await sendNotification(data)
36 | }
37 | } catch (error) {
38 | console.log('err', error)
39 | }
40 | }
41 |
42 | exports.manageTime = () => {
43 | var d = new Date()
44 | var date = d.getDate()
45 | var month = d.getMonth() + 1
46 | var year = d.getFullYear()
47 | var seconds = d.getSeconds()
48 | var minutes = d.getMinutes()
49 | var hour = d.getHours()
50 | return year + '-' + month + '-' + ' ' + hour + ':' + minutes + ':' + seconds
51 | }
52 |
53 | exports.differenceBetweenDates = (authDate, dateNow) => {
54 | return Math.ceil(Math.abs(dateNow * 1000 - authDate * 1000) / 60000)
55 | }
56 |
57 | exports.updateAndGenerateCode = async (_id, type) => {
58 | try {
59 | const code = Math.floor(100000 + Math.random() * 900000)
60 | let secureCode = {}
61 | ;(secureCode.code = code),
62 | (secureCode.expiring = Date.now() + 3600 * 20 * 5),
63 | (secureCode.type = type)
64 | await User.updateOne({ _id }, { $set: { secureCode } })
65 | return code
66 | } catch (e) {
67 | reject({ message: e.message })
68 | }
69 | }
70 |
71 | exports.isBlocked = async (user, isAuthAttempt = false) => {
72 | const currentTime = Math.floor(Date.now() / 1000)
73 | let [isBlocked, updateFields] = [false, {}]
74 |
75 | if (isAuthAttempt) {
76 | if (
77 | user.account_locked &&
78 | this.differenceBetweenDates(user.date_locked, currentTime) <
79 | process.env.lockedPeriod
80 | ) {
81 | // If the user is locked and the locked period hasn't passed yet, reset the failed attempts and keep the account locked
82 | updateFields.date_locked = currentTime
83 | updateFields.failed_count = 0
84 | isBlocked = true
85 | } else {
86 | // If the locked period has passed, unlock the account
87 | updateFields.failed_count = 0
88 | updateFields.account_locked = false
89 | isBlocked = false
90 | }
91 | } else {
92 | let failedAttempts = user.failed_count ? user.failed_count + 1 : 1
93 | updateFields.failed_count = failedAttempts
94 |
95 | if (failedAttempts === 1) {
96 | updateFields.dateFirstAttempt = currentTime
97 | }
98 |
99 | if (user.account_locked) {
100 | // If the user is already locked, reset the failed attempts and update the locked date
101 | updateFields.date_locked = currentTime
102 | updateFields.failed_count = 0
103 | isBlocked = true
104 | } else if (
105 | !user.account_locked &&
106 | failedAttempts >= process.env.bad_login_limit &&
107 | this.differenceBetweenDates(user.dateFirstAttempt, currentTime) <
108 | process.env.failInterval
109 | ) {
110 | // If the user is not locked, and they've reached the limit of failed attempts in the given interval, lock the account
111 | updateFields.account_locked = true
112 | updateFields.failed_count = 0
113 | updateFields.date_locked = currentTime
114 | isBlocked = true
115 | } else if (failedAttempts >= process.env.bad_login_limit) {
116 | // If the user has reached the limit of failed attempts but not in the given interval, reset the failed attempts count
117 | updateFields.failed_count = 1
118 | }
119 | }
120 | // If there are any changes, update the user record in the database
121 | Object.keys(updateFields).length &&
122 | (await User.updateOne({ _id: user._id }, { $set: updateFields }))
123 |
124 | return { res: isBlocked, blockedDate: currentTime, auth: isAuthAttempt }
125 | }
126 | exports.getDecimal = (symbol) => {
127 | try {
128 | let token_info = Tokens
129 |
130 | symbol =
131 | symbol === 'SATTBEP20'
132 | ? 'SATT_BEP20'
133 | : symbol === 'SATTBTT'
134 | ? 'SATT_BTT'
135 | : symbol
136 |
137 | return +token_info[symbol].dicimal
138 | } catch (err) {}
139 | }
140 |
--------------------------------------------------------------------------------
/public/privacy.html:
--------------------------------------------------------------------------------
1 | Privacy Policy of Atayen
2 |
3 |
4 | Atayen operates the https://wallet.iframe-apps.com:3014/ website, which
5 | provides the SERVICE.
6 |
7 |
8 |
9 | This page is used to inform website visitors regarding our policies with the
10 | collection, use, and disclosure of Personal Information if anyone decided to
11 | use our Service, the Atayen Oracle website.
12 |
13 |
14 |
15 | If you choose to use our Service, then you agree to the collection and use
16 | of information in relation with this policy. The Personal Information that
17 | we collect are used for providing and improving the Service. We will not use
18 | or share your information with anyone except as described in this Privacy
19 | Policy.
20 |
21 |
22 |
23 | The terms used in this Privacy Policy have the same meanings as in our Terms
24 | and Conditions, which is accessible at https://wallet.iframe-apps.com:3014/,
25 | unless otherwise defined in this Privacy Policy. Our Privacy Policy was
26 | created with the help of the
27 | Privacy Policy Template
28 | and the
29 | Online Privacy Policy Template .
32 |
33 |
34 | Information Collection and Use
35 |
36 |
37 | For a better experience while using our Service, we may require you to
38 | provide us with certain personally identifiable information, including but
39 | not limited to your name, phone number, and postal address. The information
40 | that we collect will be used to contact or identify you.
41 |
42 |
43 | Log Data
44 |
45 |
46 | We want to inform you that whenever you visit our Service, we collect
47 | information that your browser sends to us that is called Log Data. This Log
48 | Data may include information such as your computer’s Internet Protocol
49 | ("IP") address, browser version, pages of our Service that you visit, the
50 | time and date of your visit, the time spent on those pages, and other
51 | statistics.
52 |
53 |
54 | Cookies
55 |
56 |
57 | Cookies are files with small amount of data that is commonly used an
58 | anonymous unique identifier. These are sent to your browser from the website
59 | that you visit and are stored on your computer’s hard drive.
60 |
61 |
62 |
63 | Our website uses these "cookies" to collection information and to improve
64 | our Service. You have the option to either accept or refuse these cookies,
65 | and know when a cookie is being sent to your computer. If you choose to
66 | refuse our cookies, you may not be able to use some portions of our Service.
67 |
68 |
69 | Service Providers
70 |
71 |
72 | We may employ third-party companies and individuals due to the following
73 | reasons:
74 |
75 |
76 |
77 | To facilitate our Service;
78 | To provide the Service on our behalf;
79 | To perform Service-related services; or
80 | To assist us in analyzing how our Service is used.
81 |
82 |
83 |
84 | We want to inform our Service users that these third parties have access to
85 | your Personal Information. The reason is to perform the tasks assigned to
86 | them on our behalf. However, they are obligated not to disclose or use the
87 | information for any other purpose.
88 |
89 |
90 | Security
91 |
92 |
93 | We value your trust in providing us your Personal Information, thus we are
94 | striving to use commercially acceptable means of protecting it. But remember
95 | that no method of transmission over the internet, or method of electronic
96 | storage is 100% secure and reliable, and we cannot guarantee its absolute
97 | security.
98 |
99 |
100 | Links to Other Sites
101 |
102 |
103 | Our Service may contain links to other sites. If you click on a third-party
104 | link, you will be directed to that site. Note that these external sites are
105 | not operated by us. Therefore, we strongly advise you to review the Privacy
106 | Policy of these websites. We have no control over, and assume no
107 | responsibility for the content, privacy policies, or practices of any
108 | third-party sites or services.
109 |
110 |
111 | Children’s Privacy
112 |
113 |
114 | Our Services do not address anyone under the age of 13. We do not knowingly
115 | collect personal identifiable information from children under 13. In the
116 | case we discover that a child under 13 has provided us with personal
117 | information, we immediately delete this from our servers. If you are a
118 | parent or guardian and you are aware that your child has provided us with
119 | personal information, please contact us so that we will be able to do
120 | necessary actions.
121 |
122 |
123 | Changes to This Privacy Policy
124 |
125 |
126 | We may update our Privacy Policy from time to time. Thus, we advise you to
127 | review this page periodically for any changes. We will notify you of any
128 | changes by posting the new Privacy Policy on this page. These changes are
129 | effective immediately, after they are posted on this page.
130 |
131 |
132 | Contact Us
133 |
134 |
135 | If you have any questions or suggestions about our Privacy Policy, do not
136 | hesitate to contact us.
137 |
138 |
--------------------------------------------------------------------------------
/contracts/oracle.sol:
--------------------------------------------------------------------------------
1 | /**
2 | *Submitted for verification at BscScan.com on 2023-08-23
3 | */
4 |
5 | /**
6 | *Submitted for verification at BscScan.com on 2023-01-17
7 | */
8 |
9 | //SPDX-License-Identifier: Unlicense
10 |
11 |
12 | pragma solidity 0.8.19;
13 |
14 | contract owned {
15 | address payable public owner;
16 |
17 | constructor () {
18 | owner = payable(msg.sender);
19 | }
20 |
21 | modifier onlyOwner {
22 | require(msg.sender == owner,"only owner method");
23 | _;
24 | }
25 |
26 | function transferOwnership(address payable newOwner) onlyOwner public {
27 | owner = newOwner;
28 | }
29 | }
30 |
31 | contract limited is owned {
32 | mapping (address => bool) canAsk;
33 |
34 |
35 | modifier onlyCanAsk {
36 | require(canAsk[msg.sender]);
37 | _;
38 | }
39 |
40 |
41 |
42 | function changeAsk (address a,bool allow) onlyOwner public {
43 | canAsk[a] = allow;
44 | }
45 |
46 | }
47 |
48 | interface ICampaign {
49 |
50 | function update(bytes32 idRequest,uint64 likes,uint64 shares,uint64 views) external returns (bool ok);
51 | function updateBounty(bytes32 idProm,uint256 nbAbos) external returns (bool ok);
52 | }
53 |
54 | interface IERC20 {
55 | function transfer(address _to, uint256 _value) external;
56 | }
57 |
58 | contract oracle is limited {
59 |
60 | struct oracleUnit {
61 | bool granted;
62 | address token;
63 | uint256 fee;
64 | }
65 |
66 | mapping (address => oracleUnit) oracleList;
67 |
68 | modifier onlyCanAnswer {
69 | require(oracleList[msg.sender].granted || msg.sender == owner,"sender not in whitelist");
70 | _;
71 | }
72 |
73 | /**
74 | * @dev Modifier to prevent reentrancy attacks during function execution.
75 | * It sets a flag before the function body and resets it after execution.
76 | */
77 | modifier noReentrancy() {
78 | // Ensure that reentrancy is not already in progress
79 | require(!_withdrawalInProgress, "Reentrant call");
80 |
81 | _withdrawalInProgress = true; // Set the flag to prevent reentrancy
82 | _; // This underscores the location where the modified function's body will be placed.
83 | _withdrawalInProgress = false; // Reset the flag after the function completes
84 | }
85 |
86 | modifier validCampaignAddress(address campaignContract){
87 | require(campaignContract != address(0), "Invalid campaign address");
88 | _;
89 | }
90 | bool private _withdrawalInProgress; // Reentrancy guard
91 |
92 | function changeAnswer (address oracleAddress,bool allow,address token,uint256 fee) onlyOwner validCampaignAddress(oracleAddress) public {
93 | oracleList[oracleAddress] = oracleUnit(allow,token,fee);
94 |
95 | emit OracleInfoUpdated(oracleAddress, allow, token, fee);
96 | }
97 |
98 | event AskRequest(bytes32 indexed idRequest, uint8 typeSN, string idPost,string idUser);
99 | event AnswerRequest(bytes32 indexed idRequest, uint64 likes, uint64 shares, uint64 views);
100 |
101 | event AskRequestBounty( uint8 typeSN, string idPost,string idUser,bytes32 idProm);
102 | event AnswerRequestBounty(bytes32 indexed idProm,uint256 nbAbos);
103 | event OracleInfoUpdated(address indexed oracleAddress, bool allow, address token, uint256 fee);
104 |
105 |
106 | function ask (uint8 typeSN,string memory idPost,string memory idUser, bytes32 idRequest) public onlyCanAsk
107 | {
108 | emit AskRequest(idRequest, typeSN, idPost, idUser );
109 | }
110 |
111 | function askBounty(uint8 typeSN,string memory idPost,string memory idUser, bytes32 idProm) public onlyCanAsk
112 | {
113 | emit AskRequestBounty( typeSN, idPost, idUser, idProm);
114 | }
115 |
116 | function answer(address campaignContract,bytes32 idRequest,uint64 likes,uint64 shares, uint64 views) public onlyOwner validCampaignAddress(campaignContract){
117 | ICampaign campaign = ICampaign(campaignContract);
118 | campaign.update(idRequest,likes,shares,views);
119 | emit AnswerRequest(idRequest,likes,shares,views);
120 | }
121 |
122 | function answerBounty(address campaignContract,bytes32 idProm,uint256 nbAbos) public onlyOwner validCampaignAddress(campaignContract){
123 | ICampaign campaign = ICampaign(campaignContract);
124 | campaign.updateBounty(idProm,nbAbos);
125 | emit AnswerRequestBounty(idProm,nbAbos);
126 | }
127 |
128 |
129 | function thirdPartyAnswer(address campaignContract,bytes32 idRequest,uint64 likes,uint64 shares, uint64 views) public onlyCanAnswer validCampaignAddress(campaignContract) {
130 | ICampaign campaign = ICampaign(campaignContract);
131 | campaign.update(idRequest,likes,shares,views);
132 | emit AnswerRequest(idRequest,likes,shares,views);
133 |
134 |
135 | IERC20 erc20 = IERC20(oracleList[msg.sender].token);
136 | erc20.transfer(msg.sender,oracleList[msg.sender].fee);
137 | }
138 |
139 | function withdraw() onlyOwner noReentrancy public {
140 | owner.transfer(address(this).balance);
141 | }
142 |
143 | function transferToken (address token,address to,uint256 val) public onlyOwner {
144 | IERC20 erc20 = IERC20(token);
145 | erc20.transfer(to,val);
146 | }
147 |
148 | }
--------------------------------------------------------------------------------
/conf/ssl/fullchain.pem:
--------------------------------------------------------------------------------
1 | -----BEGIN CERTIFICATE-----
2 | MIIFOzCCBCOgAwIBAgISBBdHCXLMc8F8vrvzkqfPL5cEMA0GCSqGSIb3DQEBCwUA
3 | MDIxCzAJBgNVBAYTAlVTMRYwFAYDVQQKEw1MZXQncyBFbmNyeXB0MQswCQYDVQQD
4 | EwJSMzAeFw0yMjAzMDIxMjA5NTVaFw0yMjA1MzExMjA5NTRaMCYxJDAiBgNVBAMT
5 | G2FwaS1wcmVwcm9kMi5zYXR0LXRva2VuLmNvbTCCASIwDQYJKoZIhvcNAQEBBQAD
6 | ggEPADCCAQoCggEBANeC/ZH4Afmpgl03vMlsB8C8j1bBIo923XX1v5dacZgCLR/E
7 | v8zAYJ8aSCR+buesg6raTRnjrhWrel1zBvo3i3U2ciXj15THKB4ZHceFYGKdzMcg
8 | G9p23HpmlXwIePxdn6i4cQF1Zr4aXgyNmdbgH6D9EutWqsEtRYqHJMRMM1k9M2gY
9 | +/CtmggG9LugouM7RdW0WETc1BKImCX89+BuObIwmQEk4/ksA/8J2NPWy1Mc5L0P
10 | rPe6WPrH1hd4UCw3IiJzgTcKDZsHCRufm6mjEV2lUdkYCDrhRfETXE29d9jsQHbd
11 | +A2hqZxN99QFUecw+CzDAvOR0ZK3bPqs3JqCVNMCAwEAAaOCAlUwggJRMA4GA1Ud
12 | DwEB/wQEAwIFoDAdBgNVHSUEFjAUBggrBgEFBQcDAQYIKwYBBQUHAwIwDAYDVR0T
13 | AQH/BAIwADAdBgNVHQ4EFgQUQEWmx8s0a/pNj4um25ntZaqpEnwwHwYDVR0jBBgw
14 | FoAUFC6zF7dYVsuuUAlA5h+vnYsUwsYwVQYIKwYBBQUHAQEESTBHMCEGCCsGAQUF
15 | BzABhhVodHRwOi8vcjMuby5sZW5jci5vcmcwIgYIKwYBBQUHMAKGFmh0dHA6Ly9y
16 | My5pLmxlbmNyLm9yZy8wJgYDVR0RBB8wHYIbYXBpLXByZXByb2QyLnNhdHQtdG9r
17 | ZW4uY29tMEwGA1UdIARFMEMwCAYGZ4EMAQIBMDcGCysGAQQBgt8TAQEBMCgwJgYI
18 | KwYBBQUHAgEWGmh0dHA6Ly9jcHMubGV0c2VuY3J5cHQub3JnMIIBAwYKKwYBBAHW
19 | eQIEAgSB9ASB8QDvAHUAQcjKsd8iRkoQxqE6CUKHXk4xixsD6+tLx2jwkGKWBvYA
20 | AAF/SsBgXwAABAMARjBEAiAm7mzw7gwqmDp4H3rh1Yw3375thJ0Kx9y2JYqM8BXf
21 | twIgUOMFj6btNUPCPW17+vJNeqgkn25R3aTSxGGJni/LaKYAdgApeb7wnjk5IfBW
22 | c59jpXflvld9nGAK+PlNXSZcJV3HhAAAAX9KwGI+AAAEAwBHMEUCIQDOO0Qnhfes
23 | ApEKnhm4+BJQZ0qMWHm3ZoAbIM26FV7ohgIgbAM7/tVeZabR7JI1p04TErqg6uNS
24 | 0myRYs0DYLg29McwDQYJKoZIhvcNAQELBQADggEBAHmGgCnrl8L8Nrmti149fb33
25 | Itm7USX3m0nfv0EQ4r5THbjNS1+QwCO1gJkoHSg0855g1cO3sI09TGaeONpUPtpg
26 | 5ckVMlZlDYlTQU+wd7i+IGz2UpWHDfmvDBaJZ2a8obKWuI2KkLo9Pj84ajNWrfuD
27 | K2yg79PRxe+duVYnXVr8Fjrd2IF78tWOpq9QCV0SikIw4F9WW4xICM/YfzEutVrU
28 | +aETaENyQHMch263asTX0H/SmSBnMfn90pMohVc/ZCkTcww7mmeJXP6ME3DRNW/T
29 | 6AxwA2Qs8mFjDaxik48HCM2wFRgsmlWRh1k0L0I3fyTBaGVlcWDYqOnv1yGY9nk=
30 | -----END CERTIFICATE-----
31 | -----BEGIN CERTIFICATE-----
32 | MIIFFjCCAv6gAwIBAgIRAJErCErPDBinU/bWLiWnX1owDQYJKoZIhvcNAQELBQAw
33 | TzELMAkGA1UEBhMCVVMxKTAnBgNVBAoTIEludGVybmV0IFNlY3VyaXR5IFJlc2Vh
34 | cmNoIEdyb3VwMRUwEwYDVQQDEwxJU1JHIFJvb3QgWDEwHhcNMjAwOTA0MDAwMDAw
35 | WhcNMjUwOTE1MTYwMDAwWjAyMQswCQYDVQQGEwJVUzEWMBQGA1UEChMNTGV0J3Mg
36 | RW5jcnlwdDELMAkGA1UEAxMCUjMwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEK
37 | AoIBAQC7AhUozPaglNMPEuyNVZLD+ILxmaZ6QoinXSaqtSu5xUyxr45r+XXIo9cP
38 | R5QUVTVXjJ6oojkZ9YI8QqlObvU7wy7bjcCwXPNZOOftz2nwWgsbvsCUJCWH+jdx
39 | sxPnHKzhm+/b5DtFUkWWqcFTzjTIUu61ru2P3mBw4qVUq7ZtDpelQDRrK9O8Zutm
40 | NHz6a4uPVymZ+DAXXbpyb/uBxa3Shlg9F8fnCbvxK/eG3MHacV3URuPMrSXBiLxg
41 | Z3Vms/EY96Jc5lP/Ooi2R6X/ExjqmAl3P51T+c8B5fWmcBcUr2Ok/5mzk53cU6cG
42 | /kiFHaFpriV1uxPMUgP17VGhi9sVAgMBAAGjggEIMIIBBDAOBgNVHQ8BAf8EBAMC
43 | AYYwHQYDVR0lBBYwFAYIKwYBBQUHAwIGCCsGAQUFBwMBMBIGA1UdEwEB/wQIMAYB
44 | Af8CAQAwHQYDVR0OBBYEFBQusxe3WFbLrlAJQOYfr52LFMLGMB8GA1UdIwQYMBaA
45 | FHm0WeZ7tuXkAXOACIjIGlj26ZtuMDIGCCsGAQUFBwEBBCYwJDAiBggrBgEFBQcw
46 | AoYWaHR0cDovL3gxLmkubGVuY3Iub3JnLzAnBgNVHR8EIDAeMBygGqAYhhZodHRw
47 | Oi8veDEuYy5sZW5jci5vcmcvMCIGA1UdIAQbMBkwCAYGZ4EMAQIBMA0GCysGAQQB
48 | gt8TAQEBMA0GCSqGSIb3DQEBCwUAA4ICAQCFyk5HPqP3hUSFvNVneLKYY611TR6W
49 | PTNlclQtgaDqw+34IL9fzLdwALduO/ZelN7kIJ+m74uyA+eitRY8kc607TkC53wl
50 | ikfmZW4/RvTZ8M6UK+5UzhK8jCdLuMGYL6KvzXGRSgi3yLgjewQtCPkIVz6D2QQz
51 | CkcheAmCJ8MqyJu5zlzyZMjAvnnAT45tRAxekrsu94sQ4egdRCnbWSDtY7kh+BIm
52 | lJNXoB1lBMEKIq4QDUOXoRgffuDghje1WrG9ML+Hbisq/yFOGwXD9RiX8F6sw6W4
53 | avAuvDszue5L3sz85K+EC4Y/wFVDNvZo4TYXao6Z0f+lQKc0t8DQYzk1OXVu8rp2
54 | yJMC6alLbBfODALZvYH7n7do1AZls4I9d1P4jnkDrQoxB3UqQ9hVl3LEKQ73xF1O
55 | yK5GhDDX8oVfGKF5u+decIsH4YaTw7mP3GFxJSqv3+0lUFJoi5Lc5da149p90Ids
56 | hCExroL1+7mryIkXPeFM5TgO9r0rvZaBFOvV2z0gp35Z0+L4WPlbuEjN/lxPFin+
57 | HlUjr8gRsI3qfJOQFy/9rKIJR0Y/8Omwt/8oTWgy1mdeHmmjk7j1nYsvC9JSQ6Zv
58 | MldlTTKB3zhThV1+XWYp6rjd5JW1zbVWEkLNxE7GJThEUG3szgBVGP7pSWTUTsqX
59 | nLRbwHOoq7hHwg==
60 | -----END CERTIFICATE-----
61 | -----BEGIN CERTIFICATE-----
62 | MIIFYDCCBEigAwIBAgIQQAF3ITfU6UK47naqPGQKtzANBgkqhkiG9w0BAQsFADA/
63 | MSQwIgYDVQQKExtEaWdpdGFsIFNpZ25hdHVyZSBUcnVzdCBDby4xFzAVBgNVBAMT
64 | DkRTVCBSb290IENBIFgzMB4XDTIxMDEyMDE5MTQwM1oXDTI0MDkzMDE4MTQwM1ow
65 | TzELMAkGA1UEBhMCVVMxKTAnBgNVBAoTIEludGVybmV0IFNlY3VyaXR5IFJlc2Vh
66 | cmNoIEdyb3VwMRUwEwYDVQQDEwxJU1JHIFJvb3QgWDEwggIiMA0GCSqGSIb3DQEB
67 | AQUAA4ICDwAwggIKAoICAQCt6CRz9BQ385ueK1coHIe+3LffOJCMbjzmV6B493XC
68 | ov71am72AE8o295ohmxEk7axY/0UEmu/H9LqMZshftEzPLpI9d1537O4/xLxIZpL
69 | wYqGcWlKZmZsj348cL+tKSIG8+TA5oCu4kuPt5l+lAOf00eXfJlII1PoOK5PCm+D
70 | LtFJV4yAdLbaL9A4jXsDcCEbdfIwPPqPrt3aY6vrFk/CjhFLfs8L6P+1dy70sntK
71 | 4EwSJQxwjQMpoOFTJOwT2e4ZvxCzSow/iaNhUd6shweU9GNx7C7ib1uYgeGJXDR5
72 | bHbvO5BieebbpJovJsXQEOEO3tkQjhb7t/eo98flAgeYjzYIlefiN5YNNnWe+w5y
73 | sR2bvAP5SQXYgd0FtCrWQemsAXaVCg/Y39W9Eh81LygXbNKYwagJZHduRze6zqxZ
74 | Xmidf3LWicUGQSk+WT7dJvUkyRGnWqNMQB9GoZm1pzpRboY7nn1ypxIFeFntPlF4
75 | FQsDj43QLwWyPntKHEtzBRL8xurgUBN8Q5N0s8p0544fAQjQMNRbcTa0B7rBMDBc
76 | SLeCO5imfWCKoqMpgsy6vYMEG6KDA0Gh1gXxG8K28Kh8hjtGqEgqiNx2mna/H2ql
77 | PRmP6zjzZN7IKw0KKP/32+IVQtQi0Cdd4Xn+GOdwiK1O5tmLOsbdJ1Fu/7xk9TND
78 | TwIDAQABo4IBRjCCAUIwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYw
79 | SwYIKwYBBQUHAQEEPzA9MDsGCCsGAQUFBzAChi9odHRwOi8vYXBwcy5pZGVudHJ1
80 | c3QuY29tL3Jvb3RzL2RzdHJvb3RjYXgzLnA3YzAfBgNVHSMEGDAWgBTEp7Gkeyxx
81 | +tvhS5B1/8QVYIWJEDBUBgNVHSAETTBLMAgGBmeBDAECATA/BgsrBgEEAYLfEwEB
82 | ATAwMC4GCCsGAQUFBwIBFiJodHRwOi8vY3BzLnJvb3QteDEubGV0c2VuY3J5cHQu
83 | b3JnMDwGA1UdHwQ1MDMwMaAvoC2GK2h0dHA6Ly9jcmwuaWRlbnRydXN0LmNvbS9E
84 | U1RST09UQ0FYM0NSTC5jcmwwHQYDVR0OBBYEFHm0WeZ7tuXkAXOACIjIGlj26Ztu
85 | MA0GCSqGSIb3DQEBCwUAA4IBAQAKcwBslm7/DlLQrt2M51oGrS+o44+/yQoDFVDC
86 | 5WxCu2+b9LRPwkSICHXM6webFGJueN7sJ7o5XPWioW5WlHAQU7G75K/QosMrAdSW
87 | 9MUgNTP52GE24HGNtLi1qoJFlcDyqSMo59ahy2cI2qBDLKobkx/J3vWraV0T9VuG
88 | WCLKTVXkcGdtwlfFRjlBz4pYg1htmf5X6DYO8A4jqv2Il9DjXA6USbW1FzXSLr9O
89 | he8Y4IWS6wY7bCkjCWDcRQJMEhg76fsO3txE+FiYruq9RUWhiF1myv4Q6W+CyBFC
90 | Dfvp7OOGAN6dEOM4+qR9sdjoSYKEBpsr6GtPAQw4dy753ec5
91 | -----END CERTIFICATE-----
92 |
--------------------------------------------------------------------------------
/public/emailtemplate/create-tron-wallet.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 | Atayen
7 |
11 |
12 |
13 |
17 |
88 |
89 |