Raybilhelp commited on
Commit
c1099dd
·
verified ·
1 Parent(s): 6a26577

Update app.js

Browse files
Files changed (1) hide show
  1. app.js +60 -33
app.js CHANGED
@@ -1,5 +1,6 @@
1
  const express = require('express');
2
  const admin = require('firebase-admin');
 
3
 
4
  const app = express();
5
  app.use(express.json());
@@ -7,8 +8,6 @@ app.use(express.json());
7
  // ==========================================
8
  // ১. ফায়ারবেজ মাল্টিপল অ্যাডমিন সেটআপ
9
  // ==========================================
10
- // Note: Environment Variable এ FIREBASE_ADMIN_1, FIREBASE_ADMIN_3, FIREBASE_ADMIN_4 এবং
11
- // তাদের নিজ নিজ ডাটাবেজ URL (FIREBASE_DB_URL_1, 3, 4) থাকতে হবে।
12
  const initFirebase = (envAdmin, envUrl, appName) => {
13
  if (!process.env[envAdmin] || !process.env[envUrl]) {
14
  console.warn(`Warning: ${envAdmin} or ${envUrl} is missing.`);
@@ -20,9 +19,7 @@ const initFirebase = (envAdmin, envUrl, appName) => {
20
  }, appName);
21
  };
22
 
23
- // অ্যাপগুলো ইনিশিয়ালাইজ করা হচ্ছে
24
  const app1 = initFirebase('FIREBASE_ADMIN_1', 'FIREBASE_DB_URL_1', 'Admin1');
25
- // Admin 2 এর কথা লজিকে নেই, তাই ইনিশিয়ালাইজ করলাম না। প্রয়োজন হলে একই নিয়মে করতে পারবে।
26
  const app3 = initFirebase('FIREBASE_ADMIN_3', 'FIREBASE_DB_URL_3', 'Admin3');
27
  const app4 = initFirebase('FIREBASE_ADMIN_4', 'FIREBASE_DB_URL_4', 'Admin4');
28
 
@@ -51,23 +48,66 @@ const checkPostMethod = (req, res, next) => {
51
  };
52
 
53
  // ==========================================
54
- // ৪. API: রি ্যাকাউন্ট (/creataccoumt)
55
  // ==========================================
56
- app.post('/creataccoumt', checkPostMethod, async (req, res) => {
57
- const { user_id, refer_id, name, username, profile_pic_url } = req.body;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
58
 
59
- if (!user_id) return res.status(400).json({ error: 'user_id is required' });
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
60
 
61
  try {
62
  const userRef = db1.ref('user').child(user_id);
63
  const snapshot = await userRef.once('value');
64
 
65
- // যদি অ্যাকাউন্ট আগে থেকেই থাকে, রিকোয়েস্ট ক্লোজ
66
  if (snapshot.exists()) {
67
  return res.status(200).json({ message: 'Account already exists. No action taken.' });
68
  }
69
 
70
- // নতুন অ্যাকাউন্ট তৈরি
71
  const newUserData = {
72
  user_id,
73
  refer_id: refer_id || null,
@@ -82,20 +122,20 @@ app.post('/creataccoumt', checkPostMethod, async (req, res) => {
82
  };
83
  await userRef.set(newUserData);
84
 
85
- // রেফারেল লজিক (যদি refer_id থাকে)
86
  if (refer_id) {
87
  const referUserRef = db1.ref('user').child(refer_id);
88
  const referUserSnap = await referUserRef.once('value');
89
 
90
  if (referUserSnap.exists()) {
91
- // Admin 1 এ total refer +1 করা
92
  await referUserRef.child('total_refer').transaction((currentValue) => {
93
  return (currentValue || 0) + 1;
94
  });
95
 
96
- // Admin 3 তে refer/uid এ ডাটা যুক্ত করা
97
  const referListRef = db3.ref('refer').child(refer_id);
98
- await referListRef.push(user_id); // নতুন user_id লিস্টে পুশ করা হলো
 
 
 
99
  }
100
  }
101
 
@@ -107,19 +147,14 @@ app.post('/creataccoumt', checkPostMethod, async (req, res) => {
107
  });
108
 
109
  // ==========================================
110
- // . API: উইথড্র মেইন ব্যালেন্স (/withdraw-main)
111
  // ==========================================
112
- app.post('/withdraw-main', checkPostMethod, async (req, res) => {
113
  const { user_id, method, address, time, amount } = req.body;
114
  const allowedMethods = ['bkash', 'mobile-gp', 'mobile-ar', 'mobile-ro', 'mobile-bl', 'mobile-tk', 'nagad', 'binance', 'usdt', 'ton'];
115
 
116
- if (!user_id || !method || !address || !amount) {
117
- return res.status(400).json({ error: 'Missing required fields' });
118
- }
119
-
120
- if (!allowedMethods.includes(method)) {
121
- return res.status(400).json({ error: 'Invalid withdrawal method' });
122
- }
123
 
124
  try {
125
  const userRef = db1.ref('user').child(user_id);
@@ -131,15 +166,12 @@ app.post('/withdraw-main', checkPostMethod, async (req, res) => {
131
  const currentBalance = Number(userData.balance || 0);
132
  const requestAmount = Number(amount);
133
 
134
- // ব্যালেন্স চেক
135
  if (currentBalance < requestAmount) {
136
  return res.status(400).json({ error: 'Insufficient balance' });
137
  }
138
 
139
- // Admin 1 থেকে ব্যালেন্স কাটা
140
  await userRef.child('balance').set(currentBalance - requestAmount);
141
 
142
- // Admin 3 তে পেন্ডিং উইথড্র লিস্টে যুক্ত করা
143
  const pendingRef = db3.ref('withdrow/painding').child(user_id);
144
  await pendingRef.push({
145
  method,
@@ -157,13 +189,14 @@ app.post('/withdraw-main', checkPostMethod, async (req, res) => {
157
  });
158
 
159
  // ==========================================
160
- // . API: অ্যাড ব্যালেন্স উইথড্র (Admin 4 -> Admin 1)
161
  // ==========================================
162
  const adWithdrawPaths = [
163
  '/withdraw-link-visit', '/withdraw-adsgram-1', '/withdraw-adsgram-2',
164
  '/withdraw-gigapub-1', '/withdraw-gigapub-2', '/withdraw-monetag-1', '/withdraw-monetag-2'
165
  ];
166
 
 
167
  app.post(adWithdrawPaths, checkPostMethod, async (req, res) => {
168
  const { user_id, amount, method } = req.body;
169
 
@@ -171,29 +204,23 @@ app.post(adWithdrawPaths, checkPostMethod, async (req, res) => {
171
  return res.status(400).json({ error: 'Invalid request. Method must be wallet and amount is required.' });
172
  }
173
 
174
- // Path থেকে অরিজিনাল অ্যাড নেটওয়ার্কের নাম বের করা (যেমন: link-visit)
175
  const adNetworkName = req.path.replace('/withdraw-', '');
176
  const requestAmount = Number(amount);
177
 
178
  try {
179
- // Admin 4 (আগের সার্ভার) এর নির্দিষ্ট পাথে ব্যালেন্স চেক
180
  const adRef = db4.ref(adNetworkName).child(user_id);
181
  const adSnapshot = await adRef.once('value');
182
 
183
  if (!adSnapshot.exists()) return res.status(404).json({ error: 'No ad earnings found for this user' });
184
 
185
- // ধরে নিচ্ছি আগের সার্ভারে ইউজারের মোট ব্য��লেন্স `balance` নোডে আছে।
186
- // (যদি আগের সিস্টেমে ব্যালেন্স পুশ করা লিস্ট হিসেবে থাকে, তবে এখানে সেটা যোগ করার লজিক লিখতে হবে)
187
  let adCurrentBalance = Number(adSnapshot.val().balance || 0);
188
 
189
  if (adCurrentBalance < requestAmount) {
190
  return res.status(400).json({ error: 'Insufficient ad balance' });
191
  }
192
 
193
- // Admin 4 থেকে ব্যালেন্স মাইনাস করা
194
  await adRef.child('balance').set(adCurrentBalance - requestAmount);
195
 
196
- // Admin 1 এর মেইন ব্যালেন্সে ট্রান্সফার (যোগ) করা
197
  const mainUserRef = db1.ref('user').child(user_id);
198
  await mainUserRef.child('balance').transaction((currentMainBalance) => {
199
  return (currentMainBalance || 0) + requestAmount;
 
1
  const express = require('express');
2
  const admin = require('firebase-admin');
3
+ const crypto = require('crypto'); // Telegram Security-এর জন্য ইনবিল্ট মডিউল
4
 
5
  const app = express();
6
  app.use(express.json());
 
8
  // ==========================================
9
  // ১. ফায়ারবেজ মাল্টিপল অ্যাডমিন সেটআপ
10
  // ==========================================
 
 
11
  const initFirebase = (envAdmin, envUrl, appName) => {
12
  if (!process.env[envAdmin] || !process.env[envUrl]) {
13
  console.warn(`Warning: ${envAdmin} or ${envUrl} is missing.`);
 
19
  }, appName);
20
  };
21
 
 
22
  const app1 = initFirebase('FIREBASE_ADMIN_1', 'FIREBASE_DB_URL_1', 'Admin1');
 
23
  const app3 = initFirebase('FIREBASE_ADMIN_3', 'FIREBASE_DB_URL_3', 'Admin3');
24
  const app4 = initFirebase('FIREBASE_ADMIN_4', 'FIREBASE_DB_URL_4', 'Admin4');
25
 
 
48
  };
49
 
50
  // ==========================================
51
+ // ৪. Telegram Security ভ্যালিডশন মিডলওয়্যা
52
  // ==========================================
53
+ const verifyTelegramAuth = (req, res, next) => {
54
+ const { init_data, user_id, name } = req.body;
55
+
56
+ if (!init_data) return res.status(401).json({ error: 'Unauthorized: init_data is missing' });
57
+
58
+ try {
59
+ const botToken = process.env.BOT_TOKEN;
60
+ if (!botToken) return res.status(500).json({ error: 'Server configuration error' });
61
+
62
+ const urlParams = new URLSearchParams(init_data);
63
+ const hash = urlParams.get('hash');
64
+ urlParams.delete('hash');
65
+
66
+ const dataToCheck = [...urlParams.entries()]
67
+ .map(([key, value]) => `${key}=${value}`)
68
+ .sort()
69
+ .join('\n');
70
+
71
+ const secretKey = crypto.createHmac('sha256', 'WebAppData').update(botToken).digest();
72
+ const calculatedHash = crypto.createHmac('sha256', secretKey).update(dataToCheck).digest('hex');
73
+
74
+ if (calculatedHash !== hash) {
75
+ return res.status(403).json({ error: 'Forbidden: Invalid Telegram signature' });
76
+ }
77
+
78
+ const tgUser = JSON.parse(urlParams.get('user'));
79
+
80
+ // আইডি এবং নাম হুবহু সেম কি না তা চেক করা
81
+ if (String(tgUser.id) !== String(user_id)) {
82
+ return res.status(403).json({ error: 'Forbidden: User ID mismatch' });
83
+ }
84
 
85
+ const tgFullName = tgUser.last_name ? `${tgUser.first_name} ${tgUser.last_name}`.trim() : tgUser.first_name;
86
+ if (String(tgFullName) !== String(name) && String(tgUser.first_name) !== String(name)) {
87
+ return res.status(403).json({ error: 'Forbidden: Name mismatch' });
88
+ }
89
+
90
+ next(); // সব ঠিক থাকলে মূল লজিকে যাবে
91
+ } catch (error) {
92
+ console.error('Telegram Validation Error:', error);
93
+ return res.status(500).json({ error: 'Internal server error during validation' });
94
+ }
95
+ };
96
+
97
+ // ==========================================
98
+ // ৫. API: ক্রিয়েট অ্যাকাউন্ট (/creataccoumt)
99
+ // ==========================================
100
+ app.post('/creataccoumt', checkPostMethod, verifyTelegramAuth, async (req, res) => {
101
+ const { user_id, refer_id, name, username, profile_pic_url } = req.body;
102
 
103
  try {
104
  const userRef = db1.ref('user').child(user_id);
105
  const snapshot = await userRef.once('value');
106
 
 
107
  if (snapshot.exists()) {
108
  return res.status(200).json({ message: 'Account already exists. No action taken.' });
109
  }
110
 
 
111
  const newUserData = {
112
  user_id,
113
  refer_id: refer_id || null,
 
122
  };
123
  await userRef.set(newUserData);
124
 
 
125
  if (refer_id) {
126
  const referUserRef = db1.ref('user').child(refer_id);
127
  const referUserSnap = await referUserRef.once('value');
128
 
129
  if (referUserSnap.exists()) {
 
130
  await referUserRef.child('total_refer').transaction((currentValue) => {
131
  return (currentValue || 0) + 1;
132
  });
133
 
 
134
  const referListRef = db3.ref('refer').child(refer_id);
135
+ const referListSnap = await referListRef.once('value');
136
+
137
+ // Admin 3 তে refer_id না থাকলে ক্রিয়েট করে পুশ করবে, থাকলে সরাসরি পুশ করবে
138
+ await referListRef.push(user_id);
139
  }
140
  }
141
 
 
147
  });
148
 
149
  // ==========================================
150
+ // . API: উইথড্র মেইন ব্যালেন্স (/withdraw-main)
151
  // ==========================================
152
+ app.post('/withdraw-main', checkPostMethod, verifyTelegramAuth, async (req, res) => {
153
  const { user_id, method, address, time, amount } = req.body;
154
  const allowedMethods = ['bkash', 'mobile-gp', 'mobile-ar', 'mobile-ro', 'mobile-bl', 'mobile-tk', 'nagad', 'binance', 'usdt', 'ton'];
155
 
156
+ if (!method || !address || !amount) return res.status(400).json({ error: 'Missing required fields' });
157
+ if (!allowedMethods.includes(method)) return res.status(400).json({ error: 'Invalid withdrawal method' });
 
 
 
 
 
158
 
159
  try {
160
  const userRef = db1.ref('user').child(user_id);
 
166
  const currentBalance = Number(userData.balance || 0);
167
  const requestAmount = Number(amount);
168
 
 
169
  if (currentBalance < requestAmount) {
170
  return res.status(400).json({ error: 'Insufficient balance' });
171
  }
172
 
 
173
  await userRef.child('balance').set(currentBalance - requestAmount);
174
 
 
175
  const pendingRef = db3.ref('withdrow/painding').child(user_id);
176
  await pendingRef.push({
177
  method,
 
189
  });
190
 
191
  // ==========================================
192
+ // . API: অ্যাড ব্যালেন্স উইথড্র (Admin 4 -> Admin 1)
193
  // ==========================================
194
  const adWithdrawPaths = [
195
  '/withdraw-link-visit', '/withdraw-adsgram-1', '/withdraw-adsgram-2',
196
  '/withdraw-gigapub-1', '/withdraw-gigapub-2', '/withdraw-monetag-1', '/withdraw-monetag-2'
197
  ];
198
 
199
+ // এখানে verifyTelegramAuth দেওয়া হয়নি, কারণ তোমার ইনস্ট্রাকশন অনুযায়ী এটা শুধু আগের দুটোর জন্য
200
  app.post(adWithdrawPaths, checkPostMethod, async (req, res) => {
201
  const { user_id, amount, method } = req.body;
202
 
 
204
  return res.status(400).json({ error: 'Invalid request. Method must be wallet and amount is required.' });
205
  }
206
 
 
207
  const adNetworkName = req.path.replace('/withdraw-', '');
208
  const requestAmount = Number(amount);
209
 
210
  try {
 
211
  const adRef = db4.ref(adNetworkName).child(user_id);
212
  const adSnapshot = await adRef.once('value');
213
 
214
  if (!adSnapshot.exists()) return res.status(404).json({ error: 'No ad earnings found for this user' });
215
 
 
 
216
  let adCurrentBalance = Number(adSnapshot.val().balance || 0);
217
 
218
  if (adCurrentBalance < requestAmount) {
219
  return res.status(400).json({ error: 'Insufficient ad balance' });
220
  }
221
 
 
222
  await adRef.child('balance').set(adCurrentBalance - requestAmount);
223
 
 
224
  const mainUserRef = db1.ref('user').child(user_id);
225
  await mainUserRef.child('balance').transaction((currentMainBalance) => {
226
  return (currentMainBalance || 0) + requestAmount;