Deploy Bot commited on
Commit
d22e23c
Β·
1 Parent(s): 1f7206a

Retry_Implement_Full_Order_Lifecycle

Browse files
Files changed (2) hide show
  1. src/controllers/adminController.js +102 -17
  2. src/main.js +3 -0
src/controllers/adminController.js CHANGED
@@ -95,7 +95,8 @@ exports.viewOrder = async (ctx, orderId) => {
95
  let text = `πŸ“¦ **Buyurtma #${order.id}**\n` +
96
  `πŸ‘€ Mijoz: ${order.user}\n` +
97
  `πŸ“ž Tel: ${order.phone}\n` +
98
- `πŸ“… Vaqt: ${new Date(order.createdAt).toLocaleString()}\n\n` +
 
99
  `πŸ›’ **Mahsulotlar:**\n`;
100
 
101
  order.items.forEach(i => {
@@ -108,10 +109,32 @@ exports.viewOrder = async (ctx, orderId) => {
108
  ctx.replyWithLocation(order.location.latitude, order.location.longitude);
109
  }
110
 
111
- const contextKeyboard = Markup.inlineKeyboard([
112
- [Markup.button.callback("βœ… Qabul qilish", `order_accept_${order.id}`), Markup.button.callback("❌ Bekor qilish", `order_reject_${order.id}`)],
113
- [Markup.button.callback("πŸ”™ Orqaga", "admin_orders_new")]
114
- ]);
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
115
 
116
  ctx.editMessageText(text, { parse_mode: 'HTML', ...contextKeyboard })
117
  .catch(e => ctx.replyWithHTML(text, contextKeyboard));
@@ -145,27 +168,80 @@ exports.acceptOrder = async (ctx, orderId) => {
145
  try {
146
  const id = parseInt(orderId);
147
  await Order.updateOne({ id: id }, { status: 'accepted' });
148
-
149
  const order = await Order.findOne({ id: id });
150
 
151
  ctx.answerCbQuery("Buyurtma qabul qilindi βœ…");
152
 
153
- // Show Invoice Button after accept
154
- ctx.editMessageText(`βœ… **Buyurtma #${id} QABUL QILINDI**\nMijozga xabar yuborildi.`,
155
- Markup.inlineKeyboard([
156
- [Markup.button.callback("🧾 Chek chiqarish", `gen_invoice_${id}`)],
157
- [Markup.button.callback("πŸ”™ Orqaga", "admin_orders_new")]
158
- ])
159
- );
160
-
161
  if (order) {
162
- ctx.telegram.sendMessage(order.userId, `βœ… Sizning #${id} raqamli buyurtmangiz qabul qilindi! Tez orada yetkazib beriladi.`);
 
 
 
 
 
 
163
  }
 
 
 
164
  } catch (err) {
165
  console.error(err);
166
  }
167
  };
168
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
169
  // Generate Invoice Action Handler
170
  exports.showInvoice = async (ctx, orderId) => {
171
  try {
@@ -191,6 +267,7 @@ exports.rejectOrder = async (ctx, orderId) => {
191
 
192
  // Restore Stock Logic (Automatic Refund)
193
  if (order.status !== 'canceled') {
 
194
  for (const item of order.items) {
195
  await Product.updateOne({ id: item.id }, { $inc: { quantity: item.count } });
196
  }
@@ -199,11 +276,19 @@ exports.rejectOrder = async (ctx, orderId) => {
199
  await Order.updateOne({ id: id }, { status: 'canceled' });
200
 
201
  ctx.answerCbQuery("Buyurtma bekor qilindi ❌");
202
- ctx.editMessageText(`❌ **Buyurtma #${id} BEKOR QILINDI**\nOmborga qaytarildi (Refund).`, Markup.inlineKeyboard([[Markup.button.callback("πŸ”™ Orqaga", "admin_orders_new")]]));
203
 
 
204
  if (order) {
205
- ctx.telegram.sendMessage(order.userId, `❌ Sizning #${id} raqamli buyurtmangiz bekor qilindi.\n(Agar to'lov qilgan bo'lsangiz, admin bilan bog'laning)`);
 
 
 
 
 
 
206
  }
 
 
207
  } catch (err) {
208
  console.error(err);
209
  }
 
95
  let text = `πŸ“¦ **Buyurtma #${order.id}**\n` +
96
  `πŸ‘€ Mijoz: ${order.user}\n` +
97
  `πŸ“ž Tel: ${order.phone}\n` +
98
+ `πŸ“… Vaqt: ${new Date(order.createdAt).toLocaleString()}\n` +
99
+ `πŸ“Š Status: ${order.status.toUpperCase()}\n\n` +
100
  `πŸ›’ **Mahsulotlar:**\n`;
101
 
102
  order.items.forEach(i => {
 
109
  ctx.replyWithLocation(order.location.latitude, order.location.longitude);
110
  }
111
 
112
+ // Dynamic Buttons based on Status
113
+ let actionButtons = [];
114
+ if (order.status === 'new') {
115
+ actionButtons = [
116
+ [Markup.button.callback("βœ… Qabul qilish", `order_accept_${order.id}`), Markup.button.callback("❌ Bekor qilish", `order_reject_${order.id}`)]
117
+ ];
118
+ } else if (order.status === 'accepted') {
119
+ actionButtons = [
120
+ [Markup.button.callback("🧾 Chek chiqarish", `gen_invoice_${order.id}`)],
121
+ [Markup.button.callback("🚚 Yuborish (Dostavka)", `order_ship_${order.id}`)],
122
+ [Markup.button.callback("❌ Bekor qilish", `order_reject_${order.id}`)]
123
+ ];
124
+ } else if (order.status === 'shipping') {
125
+ actionButtons = [
126
+ [Markup.button.callback("🏁 Yetkazib berildi", `order_deliver_${order.id}`)],
127
+ [Markup.button.callback("❌ Bekor qilish", `order_reject_${order.id}`)]
128
+ ];
129
+ } else if (order.status === 'delivered') {
130
+ actionButtons = [
131
+ [Markup.button.callback("βœ… Bajarildi (Arxiv)", "admin_orders_new")] // Just close
132
+ ];
133
+ }
134
+
135
+ actionButtons.push([Markup.button.callback("πŸ”™ Orqaga", "admin_orders_new")]);
136
+
137
+ const contextKeyboard = Markup.inlineKeyboard(actionButtons);
138
 
139
  ctx.editMessageText(text, { parse_mode: 'HTML', ...contextKeyboard })
140
  .catch(e => ctx.replyWithHTML(text, contextKeyboard));
 
168
  try {
169
  const id = parseInt(orderId);
170
  await Order.updateOne({ id: id }, { status: 'accepted' });
 
171
  const order = await Order.findOne({ id: id });
172
 
173
  ctx.answerCbQuery("Buyurtma qabul qilindi βœ…");
174
 
175
+ // Notify User
 
 
 
 
 
 
 
176
  if (order) {
177
+ const User = require('../models/User');
178
+ const locales = require('../locales');
179
+ const user = await User.findOne({ id: order.userId });
180
+ const lang = (user && user.language) ? user.language : 'uz';
181
+ const i18n = locales[lang] || locales.uz;
182
+
183
+ ctx.telegram.sendMessage(order.userId, `${i18n.status_accepted}\nBuyurtma #${id} qabul qilindi. Tez orada aloqaga chiqamiz.`);
184
  }
185
+
186
+ // Refresh View
187
+ exports.viewOrder(ctx, id);
188
  } catch (err) {
189
  console.error(err);
190
  }
191
  };
192
 
193
+ // Ship Order
194
+ exports.shipOrder = async (ctx, orderId) => {
195
+ try {
196
+ const id = parseInt(orderId);
197
+ await Order.updateOne({ id: id }, { status: 'shipping' });
198
+ const order = await Order.findOne({ id: id });
199
+
200
+ ctx.answerCbQuery("Buyurtma yo'lga chiqdi 🚚");
201
+
202
+ // Notify User
203
+ if (order) {
204
+ const User = require('../models/User');
205
+ const locales = require('../locales');
206
+ const user = await User.findOne({ id: order.userId });
207
+ const lang = (user && user.language) ? user.language : 'uz';
208
+ const i18n = locales[lang] || locales.uz;
209
+
210
+ ctx.telegram.sendMessage(order.userId, `${i18n.status_shipping}\nBuyurtma #${id} yo'lga chiqdi (Dostavka).`);
211
+ }
212
+
213
+ exports.viewOrder(ctx, id);
214
+ } catch (e) {
215
+ console.error(e);
216
+ }
217
+ };
218
+
219
+ // Deliver Order
220
+ exports.deliverOrder = async (ctx, orderId) => {
221
+ try {
222
+ const id = parseInt(orderId);
223
+ await Order.updateOne({ id: id }, { status: 'delivered' });
224
+ const order = await Order.findOne({ id: id });
225
+
226
+ ctx.answerCbQuery("Buyurtma yetkazildi 🏁");
227
+
228
+ // Notify User
229
+ if (order) {
230
+ const User = require('../models/User');
231
+ const locales = require('../locales');
232
+ const user = await User.findOne({ id: order.userId });
233
+ const lang = (user && user.language) ? user.language : 'uz';
234
+ const i18n = locales[lang] || locales.uz;
235
+
236
+ ctx.telegram.sendMessage(order.userId, `${i18n.status_delivered}\nBuyurtma #${id} yetkazib berildi. Xaridingiz uchun rahmat!`);
237
+ }
238
+
239
+ exports.viewOrder(ctx, id);
240
+ } catch (e) {
241
+ console.error(e);
242
+ }
243
+ };
244
+
245
  // Generate Invoice Action Handler
246
  exports.showInvoice = async (ctx, orderId) => {
247
  try {
 
267
 
268
  // Restore Stock Logic (Automatic Refund)
269
  if (order.status !== 'canceled') {
270
+ const Product = require('../models/Product');
271
  for (const item of order.items) {
272
  await Product.updateOne({ id: item.id }, { $inc: { quantity: item.count } });
273
  }
 
276
  await Order.updateOne({ id: id }, { status: 'canceled' });
277
 
278
  ctx.answerCbQuery("Buyurtma bekor qilindi ❌");
 
279
 
280
+ // Notify User
281
  if (order) {
282
+ const User = require('../models/User');
283
+ const locales = require('../locales');
284
+ const user = await User.findOne({ id: order.userId });
285
+ const lang = (user && user.language) ? user.language : 'uz';
286
+ const i18n = locales[lang] || locales.uz;
287
+
288
+ ctx.telegram.sendMessage(order.userId, `${i18n.status_canceled}\nBuyurtma #${id} bekor qilindi.\n(Sabab bo'lsa admin bilan bog'laning)`);
289
  }
290
+
291
+ exports.showNewOrders(ctx);
292
  } catch (err) {
293
  console.error(err);
294
  }
src/main.js CHANGED
@@ -97,6 +97,9 @@ bot.action(/edit_prod_(.+)/, (ctx) => {
97
  bot.action(/admin_order_(.+)/, (ctx) => adminController.viewOrder(ctx, ctx.match[1]));
98
  bot.action(/order_accept_(.+)/, (ctx) => adminController.acceptOrder(ctx, ctx.match[1]));
99
  bot.action(/order_reject_(.+)/, (ctx) => adminController.rejectOrder(ctx, ctx.match[1]));
 
 
 
100
  bot.action(/delete_prod_(.+)/, (ctx) => adminController.deleteProduct(ctx, ctx.match[1]));
101
 
102
  // User Commands
 
97
  bot.action(/admin_order_(.+)/, (ctx) => adminController.viewOrder(ctx, ctx.match[1]));
98
  bot.action(/order_accept_(.+)/, (ctx) => adminController.acceptOrder(ctx, ctx.match[1]));
99
  bot.action(/order_reject_(.+)/, (ctx) => adminController.rejectOrder(ctx, ctx.match[1]));
100
+ bot.action(/order_ship_(.+)/, (ctx) => adminController.shipOrder(ctx, ctx.match[1])); // NEW
101
+ bot.action(/order_deliver_(.+)/, (ctx) => adminController.deliverOrder(ctx, ctx.match[1])); // NEW
102
+ bot.action(/gen_invoice_(.+)/, (ctx) => adminController.showInvoice(ctx, ctx.match[1]));
103
  bot.action(/delete_prod_(.+)/, (ctx) => adminController.deleteProduct(ctx, ctx.match[1]));
104
 
105
  // User Commands