Subversion Repositories SmartDukaan

Rev

Rev 37051 | Rev 37409 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
25822 amit.gupta 1
package com.spice.profitmandi.service;
2
 
3
import com.google.gson.Gson;
30025 amit.gupta 4
import com.spice.profitmandi.common.enumuration.MessageType;
29198 manish 5
import com.spice.profitmandi.common.exception.ProfitMandiBusinessException;
29927 amit.gupta 6
import com.spice.profitmandi.common.model.ProfitMandiConstants;
25822 amit.gupta 7
import com.spice.profitmandi.common.model.SendNotificationModel;
29927 amit.gupta 8
import com.spice.profitmandi.dao.entity.auth.AuthUser;
32405 jai.hind 9
import com.spice.profitmandi.dao.entity.dtr.*;
36064 aman 10
import com.spice.profitmandi.dao.entity.fofo.Customer;
25822 amit.gupta 11
import com.spice.profitmandi.dao.entity.user.Device;
32405 jai.hind 12
import com.spice.profitmandi.dao.entity.whatsapp.WhatsappMessage;
25822 amit.gupta 13
import com.spice.profitmandi.dao.model.SimpleCampaign;
14
import com.spice.profitmandi.dao.model.SimpleCampaignParams;
15
import com.spice.profitmandi.dao.repository.catalog.DeviceRepository;
29927 amit.gupta 16
import com.spice.profitmandi.dao.repository.cs.CsService;
35207 amit 17
import com.spice.profitmandi.dao.repository.cs.PartnerRegionRepository;
32405 jai.hind 18
import com.spice.profitmandi.dao.repository.dtr.*;
36064 aman 19
import com.spice.profitmandi.dao.repository.fofo.CustomerRepository;
32405 jai.hind 20
import com.spice.profitmandi.dao.repository.whatsapp.WhatsappMessageRepository;
29198 manish 21
import com.spice.profitmandi.service.user.RetailerService;
37388 vikas 22
import com.spice.profitmandi.service.whatsapp.WhatsappFlow;
32405 jai.hind 23
import com.spice.profitmandi.service.whatsapp.WhatsappMessageService;
32854 amit.gupta 24
import com.spice.profitmandi.service.whatsapp.WhatsappMessageType;
37388 vikas 25
import com.spice.profitmandi.service.whatsapp.WhatsappNumbers;
26
import com.spice.profitmandi.service.whatsapp.WhatsappProviderResolver;
32405 jai.hind 27
import org.apache.logging.log4j.LogManager;
28
import org.apache.logging.log4j.Logger;
29
import org.springframework.beans.factory.annotation.Autowired;
34522 ranu 30
import org.springframework.beans.factory.annotation.Value;
32405 jai.hind 31
import org.springframework.stereotype.Component;
25822 amit.gupta 32
 
34545 vikas.jang 33
import java.nio.charset.StandardCharsets;
32508 amit.gupta 34
import java.time.LocalDate;
32405 jai.hind 35
import java.time.LocalDateTime;
36
import java.util.*;
37
import java.util.stream.Collectors;
38
 
25835 amit.gupta 39
@Component
25822 amit.gupta 40
public class NotificationServiceImpl implements NotificationService {
41
 
35236 amit 42
    private static final Logger LOGGER = LogManager.getLogger(NotificationServiceImpl.class);
37051 amit 43
 
44
    // Region id that represents "all partners". Schemes meant for everyone are tagged to this region;
45
    // partner_region is not populated for it, so it must be expanded to all partners here.
46
    private static final int ALL_PARTNERS_REGION = 5;
47
 
32253 amit.gupta 48
    @Autowired
49
    UserCampaignRepository userCampaignRepository;
50
    @Autowired
51
    UserRepository dtrUserRepository;
52
    @Autowired
53
    UserAccountRepository userAccountRepository;
54
    @Autowired
55
    NotificationCampaignRepository notificationCampaignRepository;
56
    @Autowired
57
    DeviceRepository deviceRepository;
35207 amit 58
 
32253 amit.gupta 59
    @Autowired
35207 amit 60
    PartnerRegionRepository partnerRegionRepository;
61
 
62
 
63
    @Autowired
32253 amit.gupta 64
    FofoStoreRepository fofoStoreRepository;
65
    @Autowired
66
    CsService csService;
67
    @Autowired
68
    RetailerService retailerService;
69
    @Autowired
36064 aman 70
    CustomerRepository customerRepository;
71
    @Autowired
32253 amit.gupta 72
    PushNotificationRepository pushNotificationRepository;
73
    @Autowired
74
    private Gson gson;
34522 ranu 75
    @Value("${prod}")
76
    private boolean isProd;
25822 amit.gupta 77
 
32405 jai.hind 78
    @Autowired
32417 amit.gupta 79
    private WhatsappMessageRepository whatsappMessageRepository;
32405 jai.hind 80
 
81
    @Autowired
82
    private WhatsappMessageService whatsappMessageService;
83
 
36962 vikas 84
    @Autowired
37388 vikas 85
    private WhatsappProviderResolver whatsappProviders;
36962 vikas 86
 
32253 amit.gupta 87
    @Override
88
    public void sendNotification(SendNotificationModel sendNotificationModel) throws ProfitMandiBusinessException {
29927 amit.gupta 89
 
32253 amit.gupta 90
        SimpleCampaignParams scp = new SimpleCampaignParams();
91
        scp.setMessage(sendNotificationModel.getMessage());
92
        scp.setTitle(sendNotificationModel.getTitle());
93
        scp.setImageUrl(sendNotificationModel.getImageUrl());
94
        scp.setType(sendNotificationModel.getType());
95
        scp.setUrl(sendNotificationModel.getUrl());
96
        scp.setShowImage(sendNotificationModel.getShowImage());
97
        scp.setExpireTimestamp(sendNotificationModel.getExpiresat());
98
        SimpleCampaign sc = new SimpleCampaign(scp);
99
        sc.setSimpleCampaignParams(scp);
30025 amit.gupta 100
 
32253 amit.gupta 101
        NotificationCampaign nc = new NotificationCampaign();
102
        nc.setName(sendNotificationModel.getCampaignName());
103
        nc.setImplementationType("SimpleCampaign");
104
        nc.setImplementationParams(gson.toJson(scp));
105
        nc.setMessageType(sendNotificationModel.getMessageType());
106
        nc.setDocumentId(sendNotificationModel.getDocumentId());
107
        nc.setCreatedTimestamp(LocalDateTime.now());
108
        notificationCampaignRepository.persist(nc);
25822 amit.gupta 109
 
32253 amit.gupta 110
        Set<Integer> userIds = new HashSet<>();
111
        if (sendNotificationModel.getUserIds() != null && sendNotificationModel.getUserIds().size() > 0) {
112
            userIds.addAll(sendNotificationModel.getUserIds());
113
        }
29198 manish 114
 
32253 amit.gupta 115
        if (sendNotificationModel.getStateIds() != null && sendNotificationModel.getStateIds().size() > 0) {
33025 amit.gupta 116
            List<Integer> fofoIds = fofoStoreRepository.selectByWarehouseIds(sendNotificationModel.getStateIds()).stream()
117
                    .map(x -> x.getId()).collect(Collectors.toList());
34204 tejus.loha 118
            if (fofoIds.size() > 0) {
33025 amit.gupta 119
                userIds.addAll(userAccountRepository.selectUserIdsByRetailerIds(fofoIds));
120
            }
121
 
32253 amit.gupta 122
        }
35207 amit 123
        if(sendNotificationModel.getRegionIds() != null && sendNotificationModel.getRegionIds().size() > 0) {
37051 amit 124
            if (sendNotificationModel.getRegionIds().contains(ALL_PARTNERS_REGION)) {
125
                // "ALL partners" region: partner_region only holds a sentinel, so expand to every partner.
126
                userIds.addAll(fofoStoreRepository.selectAllDtrUserIds());
127
            } else {
128
                List<Integer> fofoIds = partnerRegionRepository.selectAllByRegionIds(sendNotificationModel.getRegionIds()).stream().map(x->x.getFofoId()).collect(Collectors.toList());
129
                if(fofoIds.size()>0) {
130
                    userIds.addAll(userAccountRepository.selectUserIdsByRetailerIds(fofoIds));
131
                }
35207 amit 132
            }
133
        }
29927 amit.gupta 134
 
34204 tejus.loha 135
        if (userIds.size() > 0) {
33025 amit.gupta 136
            for (Integer userId : userIds) {
137
                UserCampaign uc = new UserCampaign();
138
                uc.setCampaignId(nc.getId());
139
                uc.setUserId(userId);
140
                uc.setPushTimestamp(LocalDateTime.now());
141
                userCampaignRepository.persist(uc);
142
            }
143
            List<Device> devices = deviceRepository.selectByUserIdAndModifiedTimestamp(new ArrayList<>(userIds),
144
                    LocalDateTime.now().minusMonths(1), LocalDateTime.now());
145
            pushNotification(nc.getId(), devices);
146
        } else {
147
            LOGGER.info("Failed to send notification to any retailer with this model - {}", sendNotificationModel);
32253 amit.gupta 148
        }
25822 amit.gupta 149
 
32253 amit.gupta 150
    }
25822 amit.gupta 151
 
32253 amit.gupta 152
    @Override
153
    public void sendNotificationToAll(SendNotificationModel sendNotificationModel) throws ProfitMandiBusinessException {
154
        sendNotificationModel.setUserIds(fofoStoreRepository.selectAllDtrUserIds());
155
        Set<AuthUser> authUsers = new HashSet<>(
156
                csService.getAuthUserByCategoryId(ProfitMandiConstants.TICKET_CATEGORY_RBM));
157
        authUsers.addAll(csService.getAuthUserByCategoryId(ProfitMandiConstants.TICKET_CATEGORY_CATEGORY));
158
        authUsers.addAll(csService.getAuthUserByCategoryId(ProfitMandiConstants.TICKET_CATEGORY_SALES));
34903 ranu 159
        authUsers.addAll(csService.getAuthUserByCategoryId(ProfitMandiConstants.TICKET_CATEGORY_ABM));
32253 amit.gupta 160
        List<String> emailIds = authUsers.stream().map(x -> x.getEmailId()).collect(Collectors.toList());
161
        emailIds.add("devkinandan.lal@smartdukaan.com");
162
        List<User> systemUsers = dtrUserRepository.selectAllByEmailIds(emailIds);
32405 jai.hind 163
        sendNotificationModel.getUserIds()
164
                .addAll(systemUsers.stream().map(x -> x.getId()).collect(Collectors.toList()));
32253 amit.gupta 165
        this.sendNotification(sendNotificationModel);
166
    }
25822 amit.gupta 167
 
32253 amit.gupta 168
    @Override
34550 vikas.jang 169
    public void sendNotificationToSystemUsers(SendNotificationModel sendNotificationModel) throws ProfitMandiBusinessException {
170
        Set<AuthUser> authUsers = new HashSet<>(csService.getAuthUserByCategoryId(ProfitMandiConstants.TICKET_CATEGORY_RBM));
171
        authUsers.addAll(csService.getAuthUserByCategoryId(ProfitMandiConstants.TICKET_CATEGORY_CATEGORY));
172
        authUsers.addAll(csService.getAuthUserByCategoryId(ProfitMandiConstants.TICKET_CATEGORY_SALES));
34903 ranu 173
        authUsers.addAll(csService.getAuthUserByCategoryId(ProfitMandiConstants.TICKET_CATEGORY_ABM));
34550 vikas.jang 174
        List<String> emailIds = authUsers.stream().map(x -> x.getEmailId()).collect(Collectors.toList());
175
        emailIds.add("devkinandan.lal@smartdukaan.com");
176
        List<User> systemUsers = dtrUserRepository.selectAllByEmailIds(emailIds);
177
        sendNotificationModel.setUserIds(systemUsers.stream().map(x -> x.getId()).collect(Collectors.toList()));
178
        this.sendNotification(sendNotificationModel);
179
    }
180
 
181
    @Override
32405 jai.hind 182
    public void sendNotification(int fofoId, String campaignName, MessageType messageType, String title, String message)
183
            throws ProfitMandiBusinessException {
32253 amit.gupta 184
        SendNotificationModel sendNotificationModel = this.getDefaultNotificationModel();
185
        sendNotificationModel.setCampaignName(campaignName);
186
        sendNotificationModel.setMessageType(messageType);
187
        sendNotificationModel.setTitle(title);
188
        sendNotificationModel.setMessage(message);
189
        int userId = userAccountRepository.selectUserIdByRetailerId(fofoId);
190
        sendNotificationModel.setUserIds(Arrays.asList(userId));
191
        sendNotificationModel.setMessageType(MessageType.wallet);
192
        this.sendNotification(sendNotificationModel);
193
    }
25822 amit.gupta 194
 
32253 amit.gupta 195
    public SendNotificationModel getDefaultNotificationModel() {
196
        SendNotificationModel sendNotificationModel = new SendNotificationModel();
197
        sendNotificationModel.setType("url");
35840 vikas 198
        sendNotificationModel.setUrl("https://app.smartdukaan.com/pages/home/notifications");
32253 amit.gupta 199
        sendNotificationModel.setExpiresat(LocalDateTime.now().plusDays(1));
200
        sendNotificationModel.setMessageType(MessageType.notification);
201
        return sendNotificationModel;
202
    }
25822 amit.gupta 203
 
32253 amit.gupta 204
    public void pushNotification(int cid, List<Device> devices) {
29198 manish 205
 
32253 amit.gupta 206
        for (Device device : devices) {
207
            PushNotifications pn = new PushNotifications();
208
            pn.setNotificationCampaignid(cid);
209
            pn.setDeviceId(device.getId());
210
            pn.setUserId(device.getUser_id());
211
            pushNotificationRepository.persist(pn);
212
        }
29198 manish 213
 
32253 amit.gupta 214
    }
29198 manish 215
 
32253 amit.gupta 216
    @Override
34545 vikas.jang 217
    public void sendNotification(int fofoId, String campaignName, MessageType messageType, String title, String message, String url) throws ProfitMandiBusinessException {
32253 amit.gupta 218
        SendNotificationModel sendNotificationModel = this.getDefaultNotificationModel();
219
        sendNotificationModel.setCampaignName(campaignName);
220
        sendNotificationModel.setMessageType(messageType);
221
        sendNotificationModel.setTitle(title);
222
        sendNotificationModel.setMessage(message);
223
        int userId = userAccountRepository.selectUserIdByRetailerId(fofoId);
224
        sendNotificationModel.setUserIds(Arrays.asList(userId));
225
        sendNotificationModel.setMessageType(messageType);
226
        sendNotificationModel.setUrl(url);
227
        this.sendNotification(sendNotificationModel);
228
    }
29198 manish 229
 
32253 amit.gupta 230
    @Override
34545 vikas.jang 231
    public boolean sendWhatsappMessage(String message, String title, String mobile) throws Exception {
34204 tejus.loha 232
        boolean isSend=false;
34520 amit.gupta 233
        LOGGER.info("Is Prod - {}", isProd);
32874 amit.gupta 234
        if (isProd) {
37388 vikas 235
            isSend=this.sendWhatsappMessage(WhatsappFlow.GENERIC, WhatsappMessageType.TEXT, message, title, mobile, null, null);
32874 amit.gupta 236
        }
34204 tejus.loha 237
        return isSend;
32253 amit.gupta 238
    }
25822 amit.gupta 239
 
32253 amit.gupta 240
    @Override
35504 vikas 241
    public void sendADLDWhatsappMessage(String mobile) throws Exception {
242
        LOGGER.info("Is Prod - {}", isProd);
243
        if (isProd) {
244
            String message = "क्या आपने SmartDukaan Protect Plus Plan लिया है?\n\n" +
245
                    "सिर्फ ₹199 से शुरू, पाएं अपने मोबाइल के लिए 1 साल की स्मार्ट सुरक्षा —\n" +
246
                    "Liquid Damage Protection\n" +
247
                    "Accidental Damage Protection\n" +
248
                    "अपने फोन को महंगे रिपेयर खर्च से बचाएं।\n" +
249
                    "अभी जानकारी लें और अपने फोन को सुरक्षित बनाएं!";
250
            String title = "SmartDukaan से खरीदारी करने के लिए धन्यवाद!";
251
 
37388 vikas 252
            this.sendWhatsappMessage(WhatsappFlow.ADLD, WhatsappMessageType.TEXT, message, title, mobile, null, null);
35504 vikas 253
        }
254
    }
255
 
256
    @Override
36064 aman 257
    public boolean sendWhatsappInvoice(int customerId, int fofoId, String invoiceNumber, String whatsAppNo) throws Exception {
258
        boolean shouldSend = shouldSendWhatsappMessage(whatsAppNo);
259
        if (!shouldSend) return false;
260
 
261
        Customer customer = customerRepository.selectById(customerId);
262
        String mobileNumber = (whatsAppNo != null && !whatsAppNo.isEmpty()) ? whatsAppNo : customer.getMobileNumber();
263
 
264
        String message = "*SmartDukaan's One-Time Offer Unlocked!*\n" +
36194 vikas 265
                "Thank you for your purchase.\n" +
36064 aman 266
                "\n" +
36194 vikas 267
                "Abhi-abhi naya phone liya hai...\n" +
268
                "Par kya aapne uski poori suraksha li hai?\n" +
269
                "SmartDukaan par sabse kam daam mein plans available hain:\n" +
36064 aman 270
                "\n" +
36194 vikas 271
                "*Complete Protection Plan* (Accidental & Liquid Damage) - Starting ₹199\n" +
36064 aman 272
                "\n" +
36194 vikas 273
                "*Extended 1 Year Warranty* - ₹199 se shuru\n" +
36064 aman 274
                "\n" +
36194 vikas 275
                "Abhi store par iski jaankari lein.\n" +
36064 aman 276
                "\n" +
36194 vikas 277
                "*Ye offer phone ki kharidari ke sirf 24 hours tak hi valid hai!*";
36064 aman 278
 
279
        String mediaUrl = "https://partners.smartdukaan.com/wa-invoice-send/"
280
                + Base64.getMimeEncoder().encodeToString(invoiceNumber.getBytes(StandardCharsets.UTF_8)) + ".pdf";
281
        String fileName = "INV-" + invoiceNumber.replace("/", "-") + ".pdf";
282
 
283
        LOGGER.info("sendWhatsappInvoice: mobile={} mediaUrl={}", mobileNumber, mediaUrl);
37388 vikas 284
        // Goes straight to the provider rather than through sendWhatsappMediaMessage so the INVOICE flow
285
        // is named: a template-first provider needs it to pick the approved invoice template.
286
        return this.sendWhatsappMessage(WhatsappFlow.INVOICE, WhatsappMessageType.DOCUMENT, message, null,
287
                mobileNumber, mediaUrl, fileName);
36064 aman 288
    }
289
 
290
    @Override
34545 vikas.jang 291
    public boolean sendWhatsappMediaMessage(String message, String mobile, String mediaUrl, String fileName, WhatsappMessageType whatsappMessageType) throws Exception {
34204 tejus.loha 292
        boolean isSend=false;
36064 aman 293
//        if (isProd) {
294
//            isSend=this.sendWhatsappMessage(whatsappMessageType, message, null, mobile, mediaUrl, fileName);
295
//        }
37388 vikas 296
        isSend = this.sendWhatsappMessage(WhatsappFlow.GENERIC, whatsappMessageType, message, null, mobile, mediaUrl, fileName);
34204 tejus.loha 297
        return isSend;
32253 amit.gupta 298
    }
25822 amit.gupta 299
 
37388 vikas 300
    /**
301
     * Kept on this interface because cron calls it directly; it delegates to the active provider and is
302
     * a no-op for providers with no opt-in concept.
303
     */
32253 amit.gupta 304
    @Override
305
    public void optIn(String phoneNumber) throws Exception {
37388 vikas 306
        whatsappProviders.active().optIn(phoneNumber);
32253 amit.gupta 307
    }
29927 amit.gupta 308
 
37388 vikas 309
    private boolean sendWhatsappMessage(WhatsappFlow flow, WhatsappMessageType whatsappMessageType, String message,
310
                                        String title, String mobile, String mediaUrl, String fileName)
32405 jai.hind 311
            throws Exception {
37388 vikas 312
        return whatsappProviders.active()
313
                .sendBasic(flow, whatsappMessageType, message, title, mobile, mediaUrl, fileName);
32253 amit.gupta 314
    }
30025 amit.gupta 315
 
32405 jai.hind 316
    @Override
33415 amit.gupta 317
    public boolean shouldSendWhatsappMessage(String mobile) {
37388 vikas 318
        // Normalised rather than concatenated: cpass and BotPenguin store the normalised MSISDN, so for
319
        // anything that is not already a bare ten digits the old "91" + mobile key could never match a
320
        // stored row and the throttle quietly never fired. Identical result for clean input.
321
        String destAddr = WhatsappNumbers.toMsisdn(mobile);
322
        if (destAddr == null) {
323
            return true;
324
        }
33415 amit.gupta 325
        boolean shouldSend = true;
32508 amit.gupta 326
        List<WhatsappMessage> whatsappMessages = whatsappMessageRepository.selectByDestAddr(destAddr, LocalDate.now());
32405 jai.hind 327
        if (!whatsappMessages.isEmpty()) {
32508 amit.gupta 328
            long failedCount = whatsappMessages.stream().filter(x -> x.getFailed() != null && x.getFailed().equals("FAILED")).collect(Collectors.counting());
32405 jai.hind 329
            if (failedCount >= 2) {
33415 amit.gupta 330
                shouldSend = false;
32405 jai.hind 331
            }
332
        }
33415 amit.gupta 333
        return shouldSend;
32405 jai.hind 334
    }
33715 ranu 335
 
336
 
337
    @Override
338
    public void sendPaymentWhatsappMessage(String mobile, String message) throws Exception {
37388 vikas 339
        whatsappProviders.active().sendText(WhatsappFlow.PAYMENT_LINK, mobile, message);
33715 ranu 340
    }
34545 vikas.jang 341
 
25822 amit.gupta 342
}