Example #1
0
 def send(self, msg, *args, **kwargs):
     phone_number = clean_phone_number(msg.phone_number)
     config = self.config
     client = boto3.client('pinpoint',
                           region_name=config.region,
                           aws_access_key_id=config.access_key,
                           aws_secret_access_key=config.secret_access_key)
     message_request = {
         'Addresses': {
             phone_number: {
                 'ChannelType': 'SMS'
             }
         },
         'MessageConfiguration': {
             'SMSMessage': {
                 'Body': msg.text,
                 'MessageType': MESSAGE_TYPE,
                 'OriginationNumber': config.reply_to_phone_number
             }
         }
     }
     try:
         response = client.send_messages(ApplicationId=config.project_id,
                                         MessageRequest=message_request)
         msg.backend_message_id = response['MessageResponse']['Result'][
             phone_number]['MessageId']
     except ClientError as e:
         msg.set_gateway_error(e.response['Error']['Message'])
     return
Example #2
0
    def send(self, msg, *args, **kwargs):
        if self.additional_params is not None:
            params = self.additional_params.copy()
        else:
            params = {}
        
        phone_number = msg.phone_number
        if self.include_plus:
            phone_number = clean_phone_number(phone_number)
        else:
            phone_number = strip_plus(phone_number)
        
        try:
            text = msg.text.encode("iso-8859-1")
        except UnicodeEncodeError:
            text = msg.text.encode("utf-8")
        params[self.message_param] = text
        params[self.number_param] = phone_number

        url_params = urlencode(params)
        try:
            if self.method == "GET":
                response = urlopen("%s?%s" % (self.url, url_params),
                    timeout=settings.SMS_GATEWAY_TIMEOUT).read()
            else:
                response = urlopen(self.url, url_params,
                    timeout=settings.SMS_GATEWAY_TIMEOUT).read()
        except Exception as e:
            msg = "Error sending message from backend: '{}'\n\n{}".format(self.name, str(e))
            raise BackendProcessingException(msg), None, sys.exc_info()[2]
Example #3
0
def incoming(phone_number, text, backend_api, timestamp=None, domain_scope=None, backend_message_id=None, delay=True):
    """
    entry point for incoming sms

    phone_number - originating phone number
    text - message content
    backend_api - backend API ID of receiving sms backend
    timestamp - message received timestamp; defaults to now (UTC)
    domain_scope - if present, only messages from phone numbers that can be
      definitively linked to this domain will be processed; others will be
      dropped (useful to provide security when simulating incoming sms)
    """
    # Log message in message log
    phone_number = clean_phone_number(phone_number)
    msg = SMSLog(
        phone_number = phone_number,
        direction = INCOMING,
        date = timestamp or datetime.utcnow(),
        text = text,
        domain_scope = domain_scope,
        backend_api = backend_api,
        backend_message_id = backend_message_id,
    )
    if settings.SMS_QUEUE_ENABLED:
        msg.processed = False
        msg.datetime_to_process = datetime.utcnow()
        msg.queued_timestamp = msg.datetime_to_process
        msg.save()
        enqueue_directly(msg)
    else:
        msg.processed = True
        msg.save()
        process_incoming(msg, delay=delay)
    return msg
Example #4
0
    def send(self, message, delay=True, *args, **kwargs):
        """
        Send an outbound message using the Unicel API
        """
        
        phone_number = clean_phone_number(message.phone_number).replace("+", "")
        params = [(OutboundParams.DESTINATION, phone_number),
                  (OutboundParams.USERNAME, self.username),
                  (OutboundParams.PASSWORD, self.password),
                  (OutboundParams.SENDER, self.sender)]
        try:
            text = str(message.text)
            # it's ascii
            params.append((OutboundParams.MESSAGE, text))
        except UnicodeEncodeError:
            params.extend(UNICODE_PARAMS)
            encoded = message.text.encode("utf_16_be").encode("hex").upper()
            params.append((OutboundParams.MESSAGE, encoded))

        try:
            data = urlopen('%s?%s' % (OUTBOUND_URLBASE, urlencode(params))).read()
        except Exception:
            data = None

        create_billable_for_sms(message, UnicelBackend.get_api_id(), delay=delay, response=data)

        return data
Example #5
0
def send_sms(domain, contact, phone_number, text, metadata=None):
    """
    Sends an outbound SMS. Returns false if it fails.
    """
    if phone_number is None:
        return False
    if isinstance(phone_number, int) or isinstance(phone_number, long):
        phone_number = str(phone_number)
    phone_number = clean_phone_number(phone_number)

    msg = get_sms_class()(
        domain=domain,
        phone_number=phone_number,
        direction=OUTGOING,
        date=get_utcnow(),
        backend_id=None,
        location_id=get_location_id_by_contact(domain, contact),
        text = text
    )
    if contact:
        msg.couch_recipient = contact.get_id
        msg.couch_recipient_doc_type = contact.doc_type
    add_msg_tags(msg, metadata)

    return queue_outgoing_sms(msg)
Example #6
0
def send_sms(domain, id, phone_number, text):
    """
    Sends an outbound SMS. Returns false if it fails.
    """
    if phone_number is None:
        return False
    if isinstance(phone_number, int) or isinstance(phone_number, long):
        phone_number = str(phone_number)
    logging.debug('Sending message: %s' % text)
    phone_number = clean_phone_number(phone_number)
    msg = SMSLog(domain=domain,
                     couch_recipient=id, 
                     couch_recipient_doc_type="CouchUser",
                     phone_number=phone_number,
                     direction=OUTGOING,
                     date = datetime.utcnow(),
                     text = text)
    try:
        api = get_backend_api(msg)
        try:
            msg.backend_api = api.API_ID
        except Exception:
            pass
        api.send(msg)
        msg.save()
        return True
    except Exception:
        logging.exception("Problem sending SMS to %s" % phone_number)
        return False
Example #7
0
def send_sms(domain, contact, phone_number, text, metadata=None):
    """
    Sends an outbound SMS. Returns false if it fails.
    """
    if phone_number is None:
        return False
    if isinstance(phone_number, int) or isinstance(phone_number, long):
        phone_number = str(phone_number)
    phone_number = clean_phone_number(phone_number)

    msg = get_sms_class()(
        domain=domain,
        phone_number=phone_number,
        direction=OUTGOING,
        date=get_utcnow(),
        backend_id=None,
        location_id=get_location_id_by_contact(domain, contact),
        text = text
    )
    if contact:
        msg.couch_recipient = contact.get_id
        msg.couch_recipient_doc_type = contact.doc_type
    add_msg_tags(msg, metadata)

    return queue_outgoing_sms(msg)
Example #8
0
    def post(self, request, *args, **kwargs):
        context = self.get_context_data(**kwargs)

        reminder = request.POST.get('reminder')
        phone_number = context.get('phone_number')

        if reminder and phone_number:
            phone_number = clean_phone_number(phone_number)
            v = VerifiedNumber.by_phone(phone_number, include_pending=True)
            if v and v.verified:
                user = v.owner
                if reminder == 'first_soh':
                    first_soh_process_user(user, test=True)
                elif reminder == 'second_soh':
                    now = datetime.datetime.utcnow()
                    date = now - datetime.timedelta(days=5)
                    second_soh_process_user(user, date, test=True)
                elif reminder == 'third_soh':
                    third_soh_process_users_and_facilities([user], [user.location.sql_location], test=True)
                elif reminder == 'stockout':
                    stockout_process_user(user, test=True)
                elif reminder == 'rrirv':
                    rrirv_process_user(user, test=True)
                elif reminder == 'visit_website':
                    visit_website_process_user(user, test=True)
        messages.success(request, "Reminder was sent successfully")
        return self.get(request, *args, **kwargs)
Example #9
0
def send_sms(domain, contact, phone_number, text, metadata=None):
    """
    Sends an outbound SMS. Returns false if it fails.
    """
    if phone_number is None:
        return False
    if isinstance(phone_number, int) or isinstance(phone_number, long):
        phone_number = str(phone_number)
    phone_number = clean_phone_number(phone_number)

    msg = SMSLog(
        domain=domain,
        phone_number=phone_number,
        direction=OUTGOING,
        date = datetime.utcnow(),
        backend_id=None,
        text = text
    )
    if contact:
        msg.couch_recipient = contact._id
        msg.couch_recipient_doc_type = contact.doc_type
    add_msg_tags(msg, metadata)

    def onerror():
        logging.exception("Problem sending SMS to %s" % phone_number)
    return queue_outgoing_sms(msg, onerror=onerror)
Example #10
0
    def send(self, msg, *args, **kwargs):
        if self.additional_params is not None:
            params = self.additional_params.copy()
        else:
            params = {}

        phone_number = msg.phone_number
        if self.include_plus:
            phone_number = clean_phone_number(phone_number)
        else:
            phone_number = strip_plus(phone_number)

        try:
            text = msg.text.encode("iso-8859-1")
        except UnicodeEncodeError:
            text = msg.text.encode("utf-8")
        params[self.message_param] = text
        params[self.number_param] = phone_number

        url_params = urlencode(params)
        if self.method == "GET":
            response = urlopen("%s?%s" % (self.url, url_params),
                               timeout=settings.SMS_GATEWAY_TIMEOUT).read()
        else:
            response = urlopen(self.url,
                               url_params,
                               timeout=settings.SMS_GATEWAY_TIMEOUT).read()
Example #11
0
    def create(cls, message_log, multipart_count=1):
        phone_number = clean_phone_number(message_log.phone_number)
        direction = message_log.direction
        domain = message_log.domain
        log_id = message_log.couch_id

        billable = cls(
            log_id=log_id,
            phone_number=phone_number,
            direction=direction,
            date_sent=message_log.date,
            domain=domain,
        )

        gateway_charge_info = cls._get_gateway_fee(
            message_log.backend_api, message_log.backend_id, phone_number, direction, log_id,
            message_log.backend_message_id, domain
        )
        billable.gateway_fee = gateway_charge_info.gateway_fee
        billable.gateway_fee_conversion_rate = gateway_charge_info.conversion_rate
        billable.direct_gateway_fee = gateway_charge_info.direct_gateway_fee
        billable.multipart_count = cls._get_multipart_count(
            message_log.backend_api, message_log.backend_id, message_log.backend_message_id, multipart_count
        )
        billable.usage_fee = cls._get_usage_fee(domain, direction)

        if message_log.backend_api == SQLTestSMSBackend.get_api_id():
            billable.is_valid = False

        billable.save()
        return billable
Example #12
0
 def send(self, msg, *args, **kwargs):
     try:
         text = msg.text.encode("iso-8859-1")
     except UnicodeEncodeError:
         text = msg.text.encode("utf-8")
     params = urlencode({
         "phone_id" : str(self.phone_id),
         "to_number" : clean_phone_number(msg.phone_number),
         "content" : text,
         "message_type" : MESSAGE_TYPE_SMS,
     })
     url = "https://api.telerivet.com/v1/projects/%s/messages/outgoing" % str(self.project_id)
     
     curl = pycurl.Curl()
     buf = StringIO.StringIO()
     
     curl.setopt(curl.URL, url)
     curl.setopt(curl.USERPWD, "%s:" % str(self.api_key))
     curl.setopt(curl.WRITEFUNCTION, buf.write)
     curl.setopt(curl.POSTFIELDS, params)
     curl.setopt(curl.CAINFO, "%s/cacert.pem" % os.path.dirname(os.path.abspath(__file__)))
     curl.perform()
     curl.close()
     
     result = json.loads(buf.getvalue())
     buf.close()
Example #13
0
    def create(cls, message_log, multipart_count=1):
        phone_number = clean_phone_number(message_log.phone_number)
        direction = message_log.direction
        domain = message_log.domain
        log_id = message_log.couch_id

        billable = cls(
            log_id=log_id,
            phone_number=phone_number,
            direction=direction,
            date_sent=message_log.date,
            domain=domain,
        )

        gateway_charge_info = cls._get_gateway_fee(
            message_log.backend_api, message_log.backend_id, phone_number,
            direction, log_id, message_log.backend_message_id, domain)
        billable.gateway_fee = gateway_charge_info.gateway_fee
        billable.gateway_fee_conversion_rate = gateway_charge_info.conversion_rate
        billable.direct_gateway_fee = gateway_charge_info.direct_gateway_fee
        billable.multipart_count = gateway_charge_info.multipart_count or multipart_count
        billable.usage_fee = cls._get_usage_fee(domain, direction)

        if message_log.backend_api == SQLTestSMSBackend.get_api_id():
            billable.is_valid = False

        billable.save()
        return billable
Example #14
0
    def send(self, msg, *args, **kwargs):
        if self.additional_params is not None:
            params = self.additional_params.copy()
        else:
            params = {}

        phone_number = msg.phone_number
        if self.include_plus:
            phone_number = clean_phone_number(phone_number)
        else:
            phone_number = strip_plus(phone_number)

        try:
            text = msg.text.encode("iso-8859-1")
        except UnicodeEncodeError:
            text = msg.text.encode("utf-8")
        params[self.message_param] = text
        params[self.number_param] = phone_number

        url_params = urlencode(params)
        try:
            if self.method == "GET":
                response = urlopen(
                    "%s?%s" % (self.url, url_params),
                    timeout=settings.SMS_GATEWAY_TIMEOUT).read()
            else:
                response = urlopen(
                    self.url, url_params,
                    timeout=settings.SMS_GATEWAY_TIMEOUT).read()
        except Exception as e:
            msg = "Error sending message from backend: '{}'\n\n{}".format(
                self.name, str(e))
            raise BackendProcessingException(msg), None, sys.exc_info()[2]
Example #15
0
    def backend(self):
        from corehq.apps.sms.util import clean_phone_number

        if self.backend_id is not None and isinstance(self.backend_id, basestring) and self.backend_id.strip() != "":
            return MobileBackend.load_by_name(self.domain, self.backend_id)
        else:
            return MobileBackend.auto_load(clean_phone_number(self.phone_number), self.domain)
Example #16
0
    def send(self, message, delay=True, *args, **kwargs):
        """
        Send an outbound message using the Unicel API
        """

        phone_number = clean_phone_number(message.phone_number).replace(
            "+", "")
        params = [(OutboundParams.DESTINATION, phone_number),
                  (OutboundParams.USERNAME, self.username),
                  (OutboundParams.PASSWORD, self.password),
                  (OutboundParams.SENDER, self.sender)]
        try:
            text = str(message.text)
            # it's ascii
            params.append((OutboundParams.MESSAGE, text))
        except UnicodeEncodeError:
            params.extend(UNICODE_PARAMS)
            encoded = message.text.encode("utf_16_be").encode("hex").upper()
            params.append((OutboundParams.MESSAGE, encoded))

        try:
            data = urlopen('%s?%s' % (OUTBOUND_URLBASE, urlencode(params)),
                           timeout=settings.SMS_GATEWAY_TIMEOUT).read()
        except Exception:
            data = None

        return data
Example #17
0
    def send_sample_sms(self, data):
        request_token = data.get("request_token")
        if not self.get_cached_webhook_secret(request_token):
            return {"success": False, "unexpected_error": self.unexpected_error}

        outgoing_sms_form = TelerivetOutgoingSMSForm(
            {"api_key": data.get("api_key"), "project_id": data.get("project_id"), "phone_id": data.get("phone_id")}
        )

        test_sms_form = TelerivetPhoneNumberForm({"test_phone_number": data.get("test_phone_number")})

        # Be sure to call .is_valid() on both
        outgoing_sms_form_valid = outgoing_sms_form.is_valid()
        test_sms_form_valid = test_sms_form.is_valid()
        if not outgoing_sms_form_valid or not test_sms_form_valid:
            return {
                "success": False,
                "api_key_error": self.get_error_message(outgoing_sms_form, "api_key"),
                "project_id_error": self.get_error_message(outgoing_sms_form, "project_id"),
                "phone_id_error": self.get_error_message(outgoing_sms_form, "phone_id"),
                "test_phone_number_error": self.get_error_message(test_sms_form, "test_phone_number"),
            }

        tmp_backend = SQLTelerivetBackend()
        tmp_backend.set_extra_fields(
            api_key=outgoing_sms_form.cleaned_data.get("api_key"),
            project_id=outgoing_sms_form.cleaned_data.get("project_id"),
            phone_id=outgoing_sms_form.cleaned_data.get("phone_id"),
        )
        sms = SMS(
            phone_number=clean_phone_number(test_sms_form.cleaned_data.get("test_phone_number")),
            text="This is a test SMS from CommCareHQ.",
        )
        tmp_backend.send(sms)
        return {"success": True}
Example #18
0
def send(message, delay=True):
    """
    Send an outbound message using the Unicel API
    """
    config = _config()
    
    phone_number = clean_phone_number(message.phone_number).replace("+", "")
    # these are shared regardless of API
    params = [(OutboundParams.DESTINATION, phone_number),
              (OutboundParams.USERNAME, config["username"]),
              (OutboundParams.PASSWORD, config["password"]),
              (OutboundParams.SENDER, config["sender"])]
    try: 
        text = str(message.text)
        # it's ascii
        params.append((OutboundParams.MESSAGE, text))
    except UnicodeEncodeError:
        params.extend(UNICODE_PARAMS)
        encoded = message.text.encode("utf_16_be").encode("hex").upper()
        params.append((OutboundParams.MESSAGE, encoded))

    try:
        data = urlopen('%s?%s' % (OUTBOUND_URLBASE, urlencode(params))).read()
    except Exception:
        data = None
    message.save()

    create_billable_for_sms(message, API_ID, delay=delay, response=data)

    return data
Example #19
0
 def send(self, msg, *args, **kwargs):
     if self.additional_params is not None:
         params = self.additional_params.copy()
     else:
         params = {}
     
     phone_number = msg.phone_number
     if self.include_plus:
         phone_number = clean_phone_number(phone_number)
     else:
         phone_number = strip_plus(phone_number)
     
     try:
         text = msg.text.encode("iso-8859-1")
     except UnicodeEncodeError:
         text = msg.text.encode("utf-8")
     params[self.message_param] = text
     params[self.number_param] = phone_number
     
     url_params = urlencode(params)
     if self.method == "GET":
         response = urlopen("%s?%s" % (self.url, url_params),
             timeout=settings.SMS_GATEWAY_TIMEOUT).read()
     else:
         response = urlopen(self.url, url_params,
             timeout=settings.SMS_GATEWAY_TIMEOUT).read()
Example #20
0
def send_sms(domain, id, phone_number, text):
    """
    Sends an outbound SMS. Returns false if it fails.
    """
    if phone_number is None:
        return False
    if isinstance(phone_number, int) or isinstance(phone_number, long):
        phone_number = str(phone_number)
    logging.debug("Sending message: %s" % text)
    phone_number = clean_phone_number(phone_number)

    msg = SMSLog(
        domain=domain,
        couch_recipient=id,
        couch_recipient_doc_type="CouchUser",
        phone_number=phone_number,
        direction=OUTGOING,
        date=datetime.utcnow(),
        text=text,
    )

    def onerror():
        logging.exception("Problem sending SMS to %s" % phone_number)

    return send_message_via_backend(msg, onerror=onerror)
Example #21
0
 def backend(self):
     from corehq.apps.sms.util import clean_phone_number
     if self.backend_id is not None and isinstance(
             self.backend_id, basestring) and self.backend_id.strip() != "":
         return MobileBackend.load_by_name(self.domain, self.backend_id)
     else:
         return MobileBackend.auto_load(
             clean_phone_number(self.phone_number), self.domain)
Example #22
0
def incoming(phone_number, text, backend_api, timestamp=None, domain_scope=None, delay=True):
    """
    entry point for incoming sms

    phone_number - originating phone number
    text - message content
    backend_api - backend ID of receiving sms backend
    timestamp - message received timestamp; defaults to now (UTC)
    domain_scope - if present, only messages from phone numbers that can be
      definitively linked to this domain will be processed; others will be
      dropped (useful to provide security when simulating incoming sms)
    """
    phone_number = clean_phone_number(phone_number)
    v = VerifiedNumber.by_phone(phone_number, include_pending=True)
    if domain_scope:
        # only process messages for phones known to be associated with this domain
        if v is None or v.domain != domain_scope:
            raise RuntimeError("attempted to simulate incoming sms from phone number not verified with this domain")

    # Log message in message log
    msg = SMSLog(
        phone_number=phone_number,
        direction=INCOMING,
        date=timestamp or datetime.utcnow(),
        text=text,
        backend_api=backend_api,
    )
    if v is not None and v.verified:
        msg.couch_recipient_doc_type = v.owner_doc_type
        msg.couch_recipient = v.owner_id
        msg.domain = v.domain
    msg.save()

    create_billable_for_sms(msg, backend_api, delay=delay)

    if v is not None and v.verified:
        for h in settings.SMS_HANDLERS:
            try:
                handler = to_function(h)
            except:
                logging.exception("error loading sms handler: %s" % h)
                continue

            try:
                was_handled = handler(v, text)
            except:
                logging.exception("unhandled error in sms handler %s for message [%s]" % (h, text))
                was_handled = False

            if was_handled:
                break
    else:
        if not process_sms_registration(msg):
            import verify

            verify.process_verification(phone_number, text)

    return msg
Example #23
0
def send_verification(domain, user, phone_number):
    module = MobileBackend.auto_load(phone_number, domain).backend_module
    reply_phone = getattr(module, 'receive_phone_number', lambda: None)()

    message = OUTGOING % {
        'name': user.username.split('@')[0],
        'replyto': ' to %s' % util.clean_phone_number(reply_phone) if reply_phone else '',
    }
    api.send_sms(domain, user._id, phone_number, message)
Example #24
0
 def send(self, msg, orig_phone_number=None, *args, **kwargs):
     config = self.config
     to = clean_phone_number(msg.phone_number)
     try:
         self._send_text_message(config, to, msg)
         # TODO: Implement whatsapp template messages here
     except Exception:
         msg.set_system_error(SMS.ERROR_INVALID_DESTINATION_NUMBER)
         return False
Example #25
0
def send_verification(domain, user, phone_number):
    backend = MobileBackend.auto_load(phone_number, domain)
    reply_phone = backend.reply_to_phone_number

    message = OUTGOING % {
        "name": user.username.split("@")[0],
        "replyto": " to %s" % util.clean_phone_number(reply_phone) if reply_phone else "",
    }
    send_sms(domain, user, phone_number, message)
Example #26
0
    def create(cls, message_log, api_response=None):
        phone_number = clean_phone_number(message_log.phone_number)
        direction = message_log.direction

        billable = cls(
            log_id=message_log._id,
            phone_number=phone_number,
            direction=direction,
            date_sent=message_log.date,
            domain=message_log.domain,
        )

        # Fetch gateway_fee
        backend_api_id = message_log.backend_api
        backend_instance = message_log.backend_id

        country_code, national_number = get_country_code_and_national_number(phone_number)

        if backend_instance is None or _sms_backend_is_global(backend_instance):
            billable.gateway_fee = SmsGatewayFee.get_by_criteria(
                backend_api_id,
                direction,
                backend_instance=backend_instance,
                country_code=country_code,
                national_number=national_number,
            )
            if billable.gateway_fee is not None:
                conversion_rate = billable.gateway_fee.currency.rate_to_default
                if conversion_rate != 0:
                    billable.gateway_fee_conversion_rate = conversion_rate
                else:
                    smsbillables_logging.error("Gateway fee conversion rate for currency %s is 0",
                                               billable.gateway_fee.currency.code)
            else:
                smsbillables_logging.error(
                    "No matching gateway fee criteria for SMSLog %s" % message_log._id
                )

        # Fetch usage_fee todo
        domain = message_log.domain
        billable.usage_fee = SmsUsageFee.get_by_criteria(
            direction, domain=domain
        )

        if billable.usage_fee is None:
            smsbillables_logging.error("Did not find usage fee for direction %s and domain %s"
                                       % (direction, domain))

        if api_response is not None:
            billable.api_response = api_response

        if backend_api_id == TestSMSBackend.get_api_id():
            billable.is_valid = False

        billable.save()

        return billable
Example #27
0
 def outbound_backend(self):
     """appropriate outbound sms backend"""
     if self.backend_id:
         return MobileBackend.load(self.backend_id)
     else:
         return MobileBackend.auto_load(
             smsutil.clean_phone_number(self.phone_number),
             self.domain
         )
Example #28
0
def send_verification(domain, user, phone_number):
    backend = MobileBackend.auto_load(phone_number, domain)
    reply_phone = backend.reply_to_phone_number

    with localize(user.language):
        message = _(OUTGOING) % {
            'name': user.username.split('@')[0],
            'replyto': ' to %s' % util.clean_phone_number(reply_phone) if reply_phone else '',
        }
        send_sms(domain, user, phone_number, message)
Example #29
0
def send_sample_sms(request, domain):
    request_token = request.POST.get('request_token')
    if not TelerivetSetupView.get_cached_webhook_secret(request_token):
        return {
            'success': False,
            'unexpected_error': TelerivetSetupView.unexpected_error,
        }

    outgoing_sms_form = TelerivetOutgoingSMSForm({
        'api_key':
        request.POST.get('api_key'),
        'project_id':
        request.POST.get('project_id'),
        'phone_id':
        request.POST.get('phone_id'),
    })

    test_sms_form = TelerivetPhoneNumberForm({
        'test_phone_number':
        request.POST.get('test_phone_number'),
    })

    # Be sure to call .is_valid() on both
    outgoing_sms_form_valid = outgoing_sms_form.is_valid()
    test_sms_form_valid = test_sms_form.is_valid()
    if not outgoing_sms_form_valid or not test_sms_form_valid:
        return json_response({
            'success':
            False,
            'api_key_error':
            TelerivetSetupView.get_error_message(outgoing_sms_form, 'api_key'),
            'project_id_error':
            TelerivetSetupView.get_error_message(outgoing_sms_form,
                                                 'project_id'),
            'phone_id_error':
            TelerivetSetupView.get_error_message(outgoing_sms_form,
                                                 'phone_id'),
            'test_phone_number_error':
            TelerivetSetupView.get_error_message(test_sms_form,
                                                 'test_phone_number'),
        })

    tmp_backend = SQLTelerivetBackend()
    tmp_backend.set_extra_fields(
        api_key=outgoing_sms_form.cleaned_data.get('api_key'),
        project_id=outgoing_sms_form.cleaned_data.get('project_id'),
        phone_id=outgoing_sms_form.cleaned_data.get('phone_id'),
    )
    sms = SMS(phone_number=clean_phone_number(
        test_sms_form.cleaned_data.get('test_phone_number')),
              text="This is a test SMS from CommCareHQ.")
    tmp_backend.send(sms)
    return json_response({
        'success': True,
    })
Example #30
0
 def send(self, msg, *args, **kwargs):
     client = TwilioRestClient(self.account_sid, self.auth_token)
     to = msg.phone_number
     from_ = clean_phone_number(self.phone_number)
     body = msg.text
     message = client.sms.messages.create(
         body=body,
         to=to,
         from_=from_
     )
     msg.backend_message_id = message.sid
     msg.save()
Example #31
0
 def send(self, msg, delay=True, *args, **kwargs):
     phone_number = clean_phone_number(msg.phone_number)
     text = msg.text.encode("utf-8")
     params = urlencode({
         "action" : "create",
         "token" : self.messaging_token,
         "numberToDial" : phone_number,
         "msg" : text,
         "_send_sms" : "true",
     })
     url = "https://api.tropo.com/1.0/sessions?%s" % params
     response = urlopen(url, timeout=settings.SMS_GATEWAY_TIMEOUT).read()
     return response
Example #32
0
def send_verification(domain, user, phone_number):
    backend = MobileBackend.auto_load(phone_number, domain)
    reply_phone = backend.reply_to_phone_number

    with localize(user.language):
        message = _(OUTGOING) % {
            'name':
            user.username.split('@')[0],
            'replyto':
            ' to %s' %
            util.clean_phone_number(reply_phone) if reply_phone else '',
        }
        send_sms(domain, user, phone_number, message)
Example #33
0
 def send(self, msg, delay=True, *args, **kwargs):
     phone_number = clean_phone_number(msg.phone_number)
     text = msg.text.encode("utf-8")
     params = urlencode({
         "action" : "create",
         "token" : self.messaging_token,
         "numberToDial" : phone_number,
         "msg" : text,
         "_send_sms" : "true",
     })
     url = "https://api.tropo.com/1.0/sessions?%s" % params
     response = urlopen(url, timeout=settings.SMS_GATEWAY_TIMEOUT).read()
     return response
Example #34
0
def send_sms_with_backend(domain, phone_number, text, backend_id, metadata=None):
    phone_number = clean_phone_number(phone_number)
    msg = get_sms_class()(
        domain=domain,
        phone_number=phone_number,
        direction=OUTGOING,
        date=get_utcnow(),
        backend_id=backend_id,
        text=text
    )
    add_msg_tags(msg, metadata)

    return queue_outgoing_sms(msg)
Example #35
0
def send_sms_with_backend_name(domain, phone_number, text, backend_name):
    phone_number = clean_phone_number(phone_number)
    msg = SMSLog(
        domain=domain,
        phone_number=phone_number,
        direction=OUTGOING,
        date=datetime.utcnow(),
        text=text
    )

    def onerror():
        logging.exception("Exception while sending SMS to %s with backend name %s from domain %s" % (phone_number, backend_name, domain))
    return send_message_via_backend(msg, MobileBackend.load_by_name(domain, backend_name), onerror=onerror)
Example #36
0
 def get_current_verification_event(cls, domain, contact_id, phone_number):
     """
     Returns the latest phone verification event that is in progress
     for the given contact and phone number, or None if one does not exist.
     """
     qs = cls.objects.filter(
         domain=domain,
         recipient_id=contact_id,
         messagingsubevent__sms__phone_number=smsutil.clean_phone_number(phone_number),
         content_type=cls.CONTENT_PHONE_VERIFICATION,
         status=cls.STATUS_IN_PROGRESS
     )
     return qs.order_by('-date')[0] if qs.count() > 0 else None
Example #37
0
def send_sms_with_backend(domain, phone_number, text, backend_id, metadata=None):
    phone_number = clean_phone_number(phone_number)
    msg = get_sms_class()(
        domain=domain,
        phone_number=phone_number,
        direction=OUTGOING,
        date=get_utcnow(),
        backend_id=backend_id,
        text=text
    )
    add_msg_tags(msg, metadata)

    return queue_outgoing_sms(msg)
Example #38
0
    def send(self, msg, delay=True, *args, **kwargs):
        phone_number = clean_phone_number(msg.phone_number)
        text = msg.text.encode("utf-8")

        data = TEMPLATE.format(affiliate_code=escape(self.affiliate_code),
                               auth_code=escape(self.authentication_code),
                               message=escape(text),
                               msisdn=escape(phone_number))

        url = "http://www.gvi.bms9.vine.co.za/httpInputhandler/ApplinkUpload"
        req = urllib2.Request(url, data)
        response = urllib2.urlopen(req, timeout=settings.SMS_GATEWAY_TIMEOUT)
        resp = response.read()
Example #39
0
def get_backend_api(msg):
    """
    Given a message, find which version of the api to return.
    """
    # this is currently a very dumb method that checks for 
    # india and routes to unicel, otherwise returning mach
    
    # The caller assumes the returned module has a send() method 
    # that takes in a message object.
    phone = clean_phone_number(msg.phone_number)
    for code, be_module in ALTERNATIVE_BACKENDS:
        if phone.startswith(code):
            return be_module
    return DEFAULT_BACKEND
Example #40
0
def send_sms_with_backend_name(domain, phone_number, text, backend_name, metadata=None):
    phone_number = clean_phone_number(phone_number)
    backend = SQLMobileBackend.load_by_name(SQLMobileBackend.SMS, domain, backend_name)
    msg = get_sms_class()(
        domain=domain,
        phone_number=phone_number,
        direction=OUTGOING,
        date=get_utcnow(),
        backend_id=backend.couch_id,
        text=text
    )
    add_msg_tags(msg, metadata)

    return queue_outgoing_sms(msg)
Example #41
0
def send_sms_with_backend_name(domain, phone_number, text, backend_name, metadata=None):
    phone_number = clean_phone_number(phone_number)
    backend = SQLMobileBackend.load_by_name(SQLMobileBackend.SMS, domain, backend_name)
    msg = get_sms_class()(
        domain=domain,
        phone_number=phone_number,
        direction=OUTGOING,
        date=get_utcnow(),
        backend_id=backend.couch_id,
        text=text
    )
    add_msg_tags(msg, metadata)

    return queue_outgoing_sms(msg)
Example #42
0
def send_sms_with_backend_name(domain, phone_number, text, backend_name, metadata=None):
    phone_number = clean_phone_number(phone_number)
    backend = MobileBackend.load_by_name(domain, backend_name)
    msg = SMSLog(
        domain=domain,
        phone_number=phone_number,
        direction=OUTGOING,
        date=datetime.utcnow(),
        backend_id=backend._id,
        text=text
    )
    add_msg_tags(msg, metadata)

    return queue_outgoing_sms(msg)
Example #43
0
 def send(self, msg, *args, **kwargs):
     phone_number = clean_phone_number(msg.phone_number)
     text = msg.text.encode('utf-8')
     config = self.config
     params = urlencode({
         'action': 'create',
         'token': config.messaging_token,
         'numberToDial': phone_number,
         'msg': text,
         '_send_sms': 'true',
     })
     url = 'https://api.tropo.com/1.0/sessions?%s' % params
     response = urlopen(url, timeout=settings.SMS_GATEWAY_TIMEOUT).read()
     return response
Example #44
0
def send_sms_with_backend(domain, phone_number, text, backend_id, **kwargs):
    phone_number = clean_phone_number(phone_number)
    msg = SMSLog(
        domain=domain,
        phone_number=phone_number,
        direction=OUTGOING,
        date=datetime.utcnow(),
        text=text
    )
    add_msg_tags(msg, **kwargs)

    def onerror():
        logging.exception("Exception while sending SMS to %s with backend %s" % (phone_number, backend_id))
    return send_message_via_backend(msg, MobileBackend.load(backend_id), onerror=onerror)
Example #45
0
 def send(self, msg, *args, **kwargs):
     phone_number = clean_phone_number(msg.phone_number)
     text = msg.text.encode('utf-8')
     config = self.config
     params = urlencode({
         'action': 'create',
         'token': config.messaging_token,
         'numberToDial': phone_number,
         'msg': text,
         '_send_sms': 'true',
     })
     url = 'https://api.tropo.com/1.0/sessions?%s' % params
     response = urlopen(url, timeout=settings.SMS_GATEWAY_TIMEOUT).read()
     return response
Example #46
0
def incoming(phone_number,
             text,
             backend_api,
             timestamp=None,
             domain_scope=None,
             backend_message_id=None,
             raw_text=None,
             backend_id=None):
    """
    entry point for incoming sms

    phone_number - originating phone number
    text - message content
    backend_api - backend API ID of receiving sms backend
    timestamp - message received timestamp; defaults to now (UTC)
    domain_scope - set the domain scope for this SMS; see SMSBase.domain_scope for details
    """
    _py3_soft_assert(isinstance(phone_number, six.text_type),
                     '[SMS] phone_number is type %s' % type(phone_number))
    _py3_soft_assert(isinstance(text, (six.text_type, type(None))),
                     '[SMS] text is type %s' % type(text))
    _py3_soft_assert(isinstance(raw_text, (six.text_type, type(None))),
                     '[SMS] raw_text is type %s' % type(raw_text))
    # Log message in message log
    if text is None:
        text = ""
    phone_number = clean_phone_number(phone_number)
    msg = get_sms_class()(
        phone_number=phone_number,
        direction=INCOMING,
        date=timestamp or get_utcnow(),
        text=text,
        domain_scope=domain_scope,
        backend_api=backend_api,
        backend_id=backend_id,
        backend_message_id=backend_message_id,
        raw_text=raw_text,
    )
    if settings.SMS_QUEUE_ENABLED:
        msg.processed = False
        msg.datetime_to_process = get_utcnow()
        msg.queued_timestamp = msg.datetime_to_process
        msg.save()
        enqueue_directly(msg)
    else:
        msg.processed = True
        msg.save()
        process_incoming(msg)
    return msg
Example #47
0
    def send(self, msg, *args, **kwargs):
        phone_number = clean_phone_number(msg.phone_number)
        text = msg.text.encode('utf-8')

        config = self.config
        data = TEMPLATE.format(affiliate_code=escape(config.affiliate_code),
                               auth_code=escape(config.authentication_code),
                               message=escape(text),
                               msisdn=escape(phone_number))

        url = 'http://www.gvi.bms9.vine.co.za/httpInputhandler/ApplinkUpload'
        req = six.moves.urllib.request.Request(url, data)
        response = six.moves.urllib.request.urlopen(
            req, timeout=settings.SMS_GATEWAY_TIMEOUT)
        resp = response.read()
Example #48
0
    def send(self, msg, orig_phone_number=None, *args, **kwargs):
        if not orig_phone_number:
            raise Exception("Expected orig_phone_number to be passed for all "
                            "instances of PhoneLoadBalancingMixin")

        config = self.config
        client = Client(config.account_sid, config.auth_token)
        to = msg.phone_number
        msg.system_phone_number = orig_phone_number
        if toggles.WHATSAPP_MESSAGING.enabled(msg.domain) and not kwargs.get('skip_whatsapp', False):
            domain_obj = Domain.get_by_name(msg.domain)
            from_ = getattr(domain_obj, 'twilio_whatsapp_phone_number') or WHATSAPP_SANDBOX_PHONE_NUMBER
            from_ = clean_phone_number(from_)
            from_ = self.convert_to_whatsapp(from_)
            to = self.convert_to_whatsapp(to)
            messaging_service_sid = None
        else:
            from_, messaging_service_sid = self.from_or_messaging_service_sid(orig_phone_number)
        body = msg.text
        try:
            message = client.messages.create(
                body=body,
                to=to,
                from_=from_ or values.unset,
                messaging_service_sid=messaging_service_sid or values.unset,
            )
        except TwilioRestException as e:
            if e.code == INVALID_TO_PHONE_NUMBER_ERROR_CODE:
                msg.set_system_error(SMS.ERROR_INVALID_DESTINATION_NUMBER)
                return
            elif e.code == WHATSAPP_LIMITATION_ERROR_CODE:
                notify_exception(None, f"Error with Twilio Whatsapp: {e}")
                kwargs['skip_whatsapp'] = True
                self.send(msg, orig_phone_number, *args, **kwargs)
            elif e.code == TO_FROM_BLACKLIST_ERROR_CODE:
                msg.set_gateway_error("Message From/To pair violates a gateway blacklist rule")
                return
            elif e.code == REGION_PERMISSION_ERROR_CODE:
                msg.set_gateway_error("Destination region not enabled for this backend.")
                return
            elif e.code == MESSAGE_BODY_REQUIRED_ERROR_CODE:
                msg.set_gateway_error("Message body is required.")
                return
            else:
                raise

        msg.backend_message_id = message.sid
        msg.save()
Example #49
0
def incoming(phone_number,
             text,
             backend_api,
             timestamp=None,
             domain_scope=None,
             backend_message_id=None,
             delay=True,
             backend_attributes=None,
             raw_text=None):
    """
    entry point for incoming sms

    phone_number - originating phone number
    text - message content
    backend_api - backend API ID of receiving sms backend
    timestamp - message received timestamp; defaults to now (UTC)
    domain_scope - if present, only messages from phone numbers that can be
      definitively linked to this domain will be processed; others will be
      dropped (useful to provide security when simulating incoming sms)
    """
    # Log message in message log
    if text is None:
        text = ""
    phone_number = clean_phone_number(phone_number)
    msg = SMSLog(
        phone_number=phone_number,
        direction=INCOMING,
        date=timestamp or datetime.utcnow(),
        text=text,
        domain_scope=domain_scope,
        backend_api=backend_api,
        backend_message_id=backend_message_id,
        raw_text=raw_text,
    )
    if backend_attributes:
        for k, v in backend_attributes.items():
            setattr(msg, k, v)
    if settings.SMS_QUEUE_ENABLED:
        msg.processed = False
        msg.datetime_to_process = datetime.utcnow()
        msg.queued_timestamp = msg.datetime_to_process
        msg.save()
        enqueue_directly(msg)
    else:
        msg.processed = True
        msg.save()
        process_incoming(msg, delay=delay)
    return msg
Example #50
0
def send_sms(domain,
             contact,
             phone_number,
             text,
             metadata=None,
             logged_subevent=None):
    """
    Sends an outbound SMS. Returns false if it fails.
    """
    if phone_number is None:
        return False
    if isinstance(phone_number, six.integer_types):
        phone_number = str(phone_number)
    phone_number = clean_phone_number(phone_number)

    msg = get_sms_class()(domain=domain,
                          phone_number=phone_number,
                          direction=OUTGOING,
                          date=get_utcnow(),
                          backend_id=None,
                          location_id=get_location_id_by_contact(
                              domain, contact),
                          text=text)
    if contact:
        msg.couch_recipient = contact.get_id
        msg.couch_recipient_doc_type = contact.doc_type

    if domain and contact and is_commcarecase(contact):
        backend_name = contact.get_case_property('contact_backend_id')
        backend_name = backend_name.strip() if isinstance(
            backend_name, six.string_types) else ''
        soft_assert_type_text(backend_name)
        if backend_name:
            try:
                backend = SQLMobileBackend.load_by_name(
                    SQLMobileBackend.SMS, domain, backend_name)
            except BadSMSConfigException as e:
                if logged_subevent:
                    logged_subevent.error(
                        MessagingEvent.ERROR_GATEWAY_NOT_FOUND,
                        additional_error_text=six.text_type(e))
                return False

            msg.backend_id = backend.couch_id

    add_msg_tags(msg, metadata)

    return queue_outgoing_sms(msg)
Example #51
0
def incoming(phone_number,
             text,
             backend_api,
             timestamp=None,
             domain_scope=None,
             backend_message_id=None,
             raw_text=None,
             backend_id=None,
             media_urls=None):
    """
    entry point for incoming sms

    phone_number - originating phone number
    text - message content
    backend_api - backend API ID of receiving sms backend
    timestamp - message received timestamp; defaults to now (UTC)
    domain_scope - set the domain scope for this SMS; see SMSBase.domain_scope for details
    media_urls - list of urls for media download.
    """
    # Log message in message log
    if text is None:
        text = ""
    phone_number = clean_phone_number(phone_number)
    msg = get_sms_class()(
        phone_number=phone_number,
        direction=INCOMING,
        date=timestamp or get_utcnow(),
        text=text,
        domain_scope=domain_scope,
        backend_api=backend_api,
        backend_id=backend_id,
        backend_message_id=backend_message_id,
        raw_text=raw_text,
    )
    if media_urls:
        msg.custom_metadata = {"media_urls": media_urls}

    if settings.SMS_QUEUE_ENABLED:
        msg.processed = False
        msg.datetime_to_process = get_utcnow()
        msg.queued_timestamp = msg.datetime_to_process
        msg.save()
        enqueue_directly(msg)
    else:
        msg.processed = True
        msg.save()
        process_incoming(msg)
    return msg
Example #52
0
 def send(self, msg, orig_phone_number=None, *args, **kwargs):
     config = self.config
     to = clean_phone_number(msg.phone_number)
     headers = {
         'Authorization': f'App {config.auth_token}',
         'Content-Type': 'application/json',
         'Accept': 'application/json'
     }
     try:
         if config.scenario_key:
             self._send_omni_failover_message(config, to, msg, headers)
         else:
             self._send_sms(config, to, msg, headers)
     except Exception:
         msg.set_system_error(SMS.ERROR_INVALID_DESTINATION_NUMBER)
         return False
Example #53
0
def send_sms_with_backend_name(domain,
                               phone_number,
                               text,
                               backend_name,
                               metadata=None):
    phone_number = clean_phone_number(phone_number)
    backend = MobileBackend.load_by_name(domain, backend_name)
    msg = SMSLog(domain=domain,
                 phone_number=phone_number,
                 direction=OUTGOING,
                 date=datetime.utcnow(),
                 backend_id=backend._id,
                 text=text)
    add_msg_tags(msg, metadata)

    return queue_outgoing_sms(msg)
Example #54
0
    def send(self, msg, orig_phone_number=None, *args, **kwargs):
        config = self.config
        client = TurnClient(config.client_auth_token)
        to = clean_phone_number(msg.phone_number)
        try:
            wa_id = client.contacts.get_whatsapp_id(to)

            if is_whatsapp_template_message(msg.text):
                return self._send_template_message(client, wa_id, msg)
            else:
                return self._send_text_message(client, wa_id, msg)
        except WhatsAppContactNotFound:
            msg.set_system_error(SMS.ERROR_INVALID_DESTINATION_NUMBER)
            if self.config.fallback_backend_id:
                self._send_fallback_message(msg)
            return False
Example #55
0
    def create(cls, message_log, api_response=None):
        phone_number = clean_phone_number(message_log.phone_number)
        direction = message_log.direction

        billable = cls(
            log_id=message_log._id,
            phone_number=phone_number,
            direction=direction,
            date_sent=message_log.date,
        )

        # Fetch gateway_fee
        backend_api_id = message_log.backend_api
        backend_instance = message_log.backend_id

        country_code = get_country_code(phone_number)

        billable.gateway_fee = SmsGatewayFee.get_by_criteria(
            backend_api_id,
            direction,
            backend_instance=backend_instance,
            country_code=country_code)
        if billable.gateway_fee is not None:
            conversion_rate = billable.gateway_fee.currency.rate_to_default
            if conversion_rate != 0:
                billable.gateway_fee_conversion_rate = conversion_rate
            else:
                smsbillables_logging.error(
                    "Gateway fee conversion rate for currency %s is 0",
                    billable.gateway_fee.currency.code)

        # Fetch usage_fee todo
        domain = message_log.domain
        billable.usage_fee = SmsUsageFee.get_by_criteria(direction,
                                                         domain=domain)

        if billable.usage_fee is None:
            smsbillables_logging.error(
                "Did not find usage fee for direction %s and domain %s" %
                (direction, domain))

        if api_response is not None:
            billable.api_response = api_response

        billable.save()

        return billable
Example #56
0
    def post(self, request, *args, **kwargs):
        context = self.get_context_data(**kwargs)

        reminder = request.POST.get('reminder')
        phone_number = context.get('phone_number')

        if reminder and phone_number:
            phone_number = clean_phone_number(phone_number)
            v = VerifiedNumber.by_phone(phone_number, include_pending=True)
            if v and v.verified:
                user = v.owner
                if not user:
                    return self.get(request, *args, **kwargs)
                reminder_function = self.reminders.get(reminder)
                reminder_function(self.domain,
                                  datetime.utcnow(),
                                  test_list=[user])
        messages.success(request, "Reminder was sent successfully")
        return self.get(request, *args, **kwargs)
Example #57
0
def send_sms_with_backend(domain,
                          phone_number,
                          text,
                          backend_id,
                          metadata=None):
    phone_number = clean_phone_number(phone_number)
    msg = SMSLog(domain=domain,
                 phone_number=phone_number,
                 direction=OUTGOING,
                 date=datetime.utcnow(),
                 backend_id=backend_id,
                 text=text)
    add_msg_tags(msg, metadata)

    def onerror():
        logging.exception("Exception while sending SMS to %s with backend %s" %
                          (phone_number, backend_id))

    return queue_outgoing_sms(msg, onerror=onerror)
Example #58
0
    def send(self, msg, *args, **kwargs):
        text = msg.text.encode("utf-8")
        params = {
            "phone_id": str(self.phone_id),
            "to_number": clean_phone_number(msg.phone_number),
            "content": text,
            "message_type": MESSAGE_TYPE_SMS,
        }
        url = "https://api.telerivet.com/v1/projects/%s/messages/outgoing" % str(self.project_id)

        result = requests.post(
            url,
            auth=(str(self.api_key), ''),
            data=params,
            verify=True,
            timeout=settings.SMS_GATEWAY_TIMEOUT,
        )

        result = result.json()
Example #59
0
    def send(self, msg, *args, **kwargs):
        config = self.config
        if config.additional_params:
            params = config.additional_params.copy()
        else:
            params = {}

        phone_number = msg.phone_number
        if config.include_plus:
            phone_number = clean_phone_number(phone_number)
        else:
            phone_number = strip_plus(phone_number)

        try:
            text = msg.text.encode("iso-8859-1")
        except UnicodeEncodeError:
            text = msg.text.encode("utf-8")
        params[config.message_param] = text
        params[config.number_param] = phone_number

        url_params = urlencode(params)
        try:
            unverified = ssl._create_unverified_context()
            if config.method == "GET":
                urlopen(
                    "%s?%s" % (config.url, url_params),
                    context=unverified,
                    timeout=settings.SMS_GATEWAY_TIMEOUT,
                ).read()
            else:
                urlopen(
                    config.url,
                    url_params,
                    context=unverified,
                    timeout=settings.SMS_GATEWAY_TIMEOUT,
                ).read()
        except Exception as e:
            msg = "Error sending message from backend: '{}'\n\n{}".format(
                self.pk, str(e))
            six.reraise(BackendProcessingException,
                        BackendProcessingException(msg),
                        sys.exc_info()[2])
Example #60
0
    def send(self, msg, *args, **kwargs):
        phone_number = clean_phone_number(msg.phone_number)
        text = msg.text

        config = self.config
        data = TEMPLATE.format(affiliate_code=escape(config.affiliate_code),
                               auth_code=escape(config.authentication_code),
                               message=escape(text),
                               msisdn=escape(phone_number))

        url = 'http://www.gvi.bms9.vine.co.za/httpInputhandler/ApplinkUpload'

        response = requests.post(
            url,
            data=data.encode('utf-8'),
            headers={'content-type': 'text/xml'},
            timeout=settings.SMS_GATEWAY_TIMEOUT,
        )

        self.handle_response(response)