odeo.py 13.7 KB
import base64
import json

import requests
from opensipkd.base import get_settings

from .vendor import VendorClass

from ..tools import log
import urllib3

urllib3.disable_warnings()


class Vendor(VendorClass):
    def __init__(self, vendor_produk, invoice_det):
        VendorClass.__init__(self, vendor_produk, invoice_det=invoice_det)
        # id_pel, customer_id, cust_trx, row
        settings = get_settings()
        self.mid = 'odeo_mid' in settings and settings['odeo_mid'] or None
        self.key = 'odeo_key' in settings and settings['odeo_key'] or None
        self.url = 'odeo_url' in settings and settings['odeo_url'] or None
        key = ":".join([self.mid, self.key]).encode()
        self.auth = base64.b64encode(key).decode()

    def request_post(self, params, url=None):
        headers = {'Authorization': 'Bearer {key}'.format(key=self.auth)}
        data = json.dumps(params)
        self.url = url and self.url + url or self.url
        try:
            with requests.session():
                resp = requests.post(self.url, data=data,
                                     verify=False, headers=headers)
        except:
            resp = None

        return resp

    def request_get(self, params, url=None):
        headers = {'Authorization': 'Bearer {key}'.format(key=self.auth)}
        self.url = url and self.url + url or self.url
        try:

            with requests.session():
                resp = requests.get(self.url, params=params,
                                verify=False, headers=headers)
        except:
            resp = None

        return resp

    def inquiry(self):
        if not self.v_produk_kd or not self.id_pel:
            return dict(code=9999,
                        message='Parameter tidak lengkap')

        if self.v_produk_kd[:3] == 'PLN' and self.v_produk_kd != 'PLNPASCA':
            params = dict(
                number=self.id_pel
            )

            self.request = params
            log.info("ODEO Inquiry Request: %s" % params)
            self.save_log("inquiry")
            resp = self.request_get(params, '/prepaid/pln/inquiry')
        else:
            params = dict(
                denom=self.v_produk_kd,
                number=self.id_pel
            )
            self.request = params
            self.save_log("inquiry")
            log.info("ODEO Inquiry Request: %s" % params)
            resp = self.request_get(params, '/postpaid/inquiry')

        try:
            result = json.loads(resp.text)
        except:
            result = resp.text

        log.info("ODEO Inquiry Response: %s" % result)

        if resp.ok:
            self.status = 1  # sukses
            data = "data" in result and result["data"] or None
            parsd = self.pars_data(data)
            if parsd:
                parsd.update(code=0,
                             status="SUCCES")

        elif resp.status_code == 400:
            self.status = -1
            message = "data" in result and result["data"] or ""
            message = message and "errors" in message and message["errors"] or message
            message = type(message) is list and ", ".join(message) or message

            parsd = dict(code=resp.status_code,
                         message=message)
        else:
            self.status = -1
            parsd = dict(code=500,
                         message="Other Error")
        if not parsd:
            parsd = dict(code=500,
                         message="Other Error")

        self.response = result
        log.info("Response To Cust: %s" % parsd)
        self.result = parsd
        self.save_log('inquiry')
        return parsd


    def gagal_transaksi(self, code):
        if code==400:
            self.status = -3
        else:
            self.status = -2

        parsd = dict(
            status="FAILED",
            code=code,
            message="Gagal Transaksi"
        )
        self.result = parsd
        self.save_log('payment')
        return parsd

    def payment(self):
        params = dict(
            data=dict(
                denom=self.v_produk_kd,
                number=self.id_pel
            )
        )
        self.request = params
        log.info("ODEO Payment Request: %s" % self.request)
        self.save_log("payment")
        resp = self.request_post(params, '/prepaid/purchase')
        try:
            result = json.loads(resp.text)
        except:
            result = resp.text

        self.response = result
        log.info("ODEO Payment Response: %s" % self.response)
        # odeo mengembalikan result dalam bentuk status
        # 0200 ok
        # 0400 bad request
        # 0401 auth error
        parsd = {}
        if resp.status_code == 200:  # 0200
            data = "data" in result and result["data"] or None
            # cel rc status
            if not data:
                return self.gagal_transaksi(500)

            if "rc" in data:
                parsd["code"] = int(data["rc"])

                if data["rc"] == "13":
                    parsd["status"] = "FAILED"
                    self.status = -2
                elif data["rc"] == "68":
                    parsd["status"] = "PENDING"
                    self.status = -1  # pending
                elif data["rc"] == "67":
                    parsd["status"] = "DOUBLE"
                    self.status = -2  # Gagal Karena Pernah Transaksi
                    # Status ini hanya sementara nunggu refund
                    # Status -2 ini harus dicari solusi mencari vendor lain
            else:
                self.status = 1
                parsd["code"] = 0
                parsd["status"] = "SUCCESS"
                self.serial_number = 'serial_number' in data and data["serial_numner"] \
                                     or self.serial_number

            self.vend_inv_no = "order_id" in data and data["order_id"] or None
            self.amt_buy = "price" in data and data["price"] or 0

            parsd["total"] = self.amt_buy
            self.result = parsd
            self.save_log('payment')
            return  parsd

        else:  # BAD REQUEST

            return self.gagal_transaksi(resp.status_code)


    def advice(self):
        if not self.v_produk_kd or not self.id_pel or not self.invoice_det:
            return dict(code=9999,
                        message='Parameter tidak lengkap')

        if self.kategori == 'e-payment':
            order_id = self.invoice_det.vend_inv_no
            url = '/order/{order_id}'.format(order_id=order_id)
            params = None
            self.request = url
        else:
            params = dict(
                data=dict(
                    denom=self.v_produk_kd,
                    number=self.id_pel
                )
            )
            self.request = params
            self.save_log("advice")
            url = '/prepaid/purchase-get'

        self.save_log("advice")
        resp = self.request_get(params, url)
        try:
            result = json.loads(resp.text)
        except:
            result = resp.text

        if resp.ok:
            self.status = 1  # sukses
            data = "data" in result and result["data"] or None
            parsd = self.pars_data(data)

        elif resp.status_code == 400:
            self.status = -3
            parsd = dict(code=resp.status_code,
                         message=resp.text)
        else:
            self.status = -4
            parsd = dict(code=500,
                         message="Other Error")

        self.response = result
        self.save_log('advice')
        return parsd

    def pars_data(self, data):
        result = dict()
        if not data:
            return result

        if "subscriber_id" in data and data["subscriber_id"]:
            result['id_pel'] = data["subscriber_id"]
        if "name" in data and data["name"]:
            result['nama'] = data["name"]
        if "subscriber_name" in data and data["subscriber_name"]:
            result['nama'] = data["subscriber_name"]
        if "ref_id" in data and data["ref_id"]:
            result['ref_no'] = data["ref_id"]
        if "subtotal" in data and data["subtotal"]:
            result['subtotal'] = data["subtotal"]
        if "discount" in data and data["discount"]:
            result['discount'] = data["discount"]
        if "total" in data and data["total"]:
            result['total'] = data["total"]
        if "tarif" in data and data["tariff"]:
            result['tarif'] = data["tariff"]

        rincian = {}
        if "number" in data:
            rincian['no_meter'] = data["number"]
        if "power" in data:
            rincian['daya'] = data["power"]

        inquiries = 'inquiries' in data and data['inquiries'] \
                    or 'inquiry' in data and data['inquiry'] or {}
        if not inquiries:
            result["jml_data"] = 1
            result["rincian"] = rincian
            return result

        if self.v_produk_kd == "PLNPASCA" or self.v_produk_kd[:3] == "PAM":
            pokok = denda = admin = 0
            period = meter = ""
            jml_period = 0
            i = 0
            for inq in inquiries:
                pokok += inq["base_price"]
                denda += inq["fine"]
                if "admin" in inq:
                    admin += inq["admin"]
                if "admin_fee" in inq:
                    admin += inq["admin_fee"]
                period += "period" in inq and inq["period"] + " "
                jml_period += 1
                if "meter_changes" in inq:
                    meter += inq["meter_changes"]
                i+=1

            rincian["pokok"] = pokok
            rincian["denda"] = denda
            rincian["admin"] = admin
            rincian["period"] = period
            rincian["jml_bulan"] = jml_period
            if meter:
                result["meter"] = meter

        else:
            inquirieses = type(inquiries) is list and inquiries or [inquiries]
            i = 0
            for inquiries in inquirieses:
                # if "name" in inquiries:
                #     result['nama'] = inquiries["name"]
                #
                # if "tariff" in inquiries:
                #     result['tarif'] = inquiries["tariff"]
                # if "power" in data:
                #     result['daya'] = data["power"]
                #
                if "base_price" in inquiries:
                    if "pokok" in rincian:
                        rincian['pokok'] += inquiries["base_price"]
                    else:
                        rincian['pokok'] = inquiries["base_price"]

                if "fine" in inquiries:
                    if "denda" in rincian:
                        rincian['denda'] += inquiries["fine"]
                    else:
                        rincian['denda'] = inquiries["fine"]

                if "coll_fee" in inquiries:
                    if "coll_fee" in rincian:
                        rincian['coll_fee'] += inquiries["coll_fee"]
                    else:
                        rincian['coll_fee'] = inquiries["coll_fee"]

                if "bill_rest" in inquiries:
                    if "restitusi" in rincian:
                        rincian['restitusi'] += inquiries["bill_rest"]
                    else:
                        rincian['restitusi'] = inquiries["bill_rest"]

                if "admin" in inquiries:
                    if "admin" in rincian:
                        rincian['admin'] += inquiries["admin"]
                    else:
                        rincian['admin'] = inquiries["admin"]

                if "admin_fee" in inquiries:
                    if "admin" in rincian:
                        rincian['admin'] += inquiries["admin_fee"]
                    else:
                        rincian['admin'] = inquiries["admin_fee"]

                if "period" in inquiries:
                    if "period" in rincian:
                        rincian['period'] += " " + inquiries["period"]
                    else:
                        rincian['period'] = inquiries["period"]

                if "meter_changes" in inquiries:
                    if "meter" in rincian:
                        rincian['meter'] += inquiries["meter_changes"]
                    else:
                        rincian['meter'] = inquiries["meter_changes"]

                if "usages" in inquiries:
                    if "penggunaan" in rincian:
                        rincian['penggunaan'] += inquiries["usages"]
                    else:
                        rincian['penggunaan'] = inquiries["usages"]

                if "installment" in inquiries:
                    if "periode" in rincian:
                        rincian['periode'] += " " + inquiries["installment"]
                    else:
                        rincian['periode'] = inquiries["installment"]

                if "due_date" in inquiries:
                    if "jth_tempo" in rincian:
                        rincian['jth_tempo'] += " " + inquiries["due_date"]
                    else:
                        rincian['jth_tempo'] = inquiries["due_date"]

                if "branch_code" in inquiries:
                    rincian['kd_cabang'] = inquiries["branch_code"]

                if "branch_name" in inquiries:
                    rincian['nm_cabang'] = inquiries["branch_name"]

                if "month_counts" in inquiries:
                    rincian['jml_bulan'] = inquiries["month_counts"]

                if "participant_counts" in inquiries:
                    rincian['anggota'] = inquiries["participant_counts"]

                i += 1
        self.amt_buy = result["total"]
        jual = self.vendor_produk.produk.harga*i
        self.discount = rincian["admin"] - jual
        self.amt_sell = rincian["subtotal"] - self.discount
        result["discount"] = self.discount
        result["total"] = self.amt_sell
        result['jml_data'] = i
        result['rincian'] = rincian

        return result