package cc.blynk.server.hardware.handlers.hardware.logic; import cc.blynk.server.core.model.DashBoard; import cc.blynk.server.core.model.widgets.notifications.SMS; import cc.blynk.server.core.processors.NotificationBase; import cc.blynk.server.core.protocol.exceptions.NotificationBodyInvalidException; import cc.blynk.server.core.protocol.model.messages.StringMessage; import cc.blynk.server.core.session.HardwareStateHolder; import cc.blynk.server.notifications.sms.SMSWrapper; import io.netty.channel.Channel; import io.netty.channel.ChannelHandlerContext; import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.Logger; import static cc.blynk.server.core.protocol.enums.Response.NOTIFICATION_ERROR; import static cc.blynk.server.core.protocol.enums.Response.NOTIFICATION_NOT_AUTHORIZED; import static cc.blynk.utils.BlynkByteBufUtil.makeResponse; import static cc.blynk.utils.BlynkByteBufUtil.ok; /** * Sends tweets from hardware. * * The Blynk Project. * Created by Dmitriy Dumanskiy. * Created on 2/1/2015. * */ public class SmsLogic extends NotificationBase { private static final Logger log = LogManager.getLogger(SmsLogic.class); private static final int MAX_SMS_BODY_SIZE = 160; private final SMSWrapper smsWrapper; public SmsLogic(SMSWrapper smsWrapper, long notificationQuotaLimit) { super(notificationQuotaLimit); this.smsWrapper = smsWrapper; } public void messageReceived(ChannelHandlerContext ctx, HardwareStateHolder state, StringMessage message) { if (message.body == null || message.body.isEmpty() || message.body.length() > MAX_SMS_BODY_SIZE) { throw new NotificationBodyInvalidException(); } DashBoard dash = state.user.profile.getDashByIdOrThrow(state.dashId); SMS smsWidget = dash.getWidgetByType(SMS.class); if (smsWidget == null || !dash.isActive || smsWidget.to == null || smsWidget.to.isEmpty()) { log.debug("User has no access phone number provided."); ctx.writeAndFlush(makeResponse(message.id, NOTIFICATION_NOT_AUTHORIZED), ctx.voidPromise()); return; } checkIfNotificationQuotaLimitIsNotReached(); log.trace("Sending sms for user {}, with message : '{}'.", state.user.email, message.body); sms(ctx.channel(), state.user.email, smsWidget.to, message.body, message.id); } private void sms(Channel channel, String email, String to, String body, int msgId) { try { smsWrapper.send(to, body); channel.writeAndFlush(ok(msgId), channel.voidPromise()); } catch (Exception e) { log.error("Error sending sms for user {}. Reason : {}", email, e.getMessage()); channel.writeAndFlush(makeResponse(msgId, NOTIFICATION_ERROR), channel.voidPromise()); } } }