Пример #1
0
def get_products():
    dbg('get_products')
    reply, status_code = {'code': 0, 'msg': ''}, 200

    try:
        data = request.get_json()

        # cat 和 device_id 二选一
        cat = data.get('cat')
        device_id = data.get('device_id')
    except:
        print_exception_info()
        raise ApiError('get products error', error.ERROR_PARAM)

    data = []
    if cat is not None:
        agent_id = current_user.agent_id
        products = dbapi.get_product(agent_id=agent_id, cat=cat)
        if products:
            for product in products:
                info = {
                    'id': product.id,
                    'cat': product.cat,
                    'title': product.title,
                    'body': product.body,
                    'value': product.value,
                    'price': product.price,
                    'inventory': product.inventory
                }
                data.append(info)

    if device_id is not None:
        device = dbapi.get_device(device_id=device_id)
        if not device:
            raise ApiError('ERROR_DEVICE_NOT_FOUND',
                           error.ERROR_DEVICE_NOT_FOUND)
        device_products = dbapi.get_device_product(device_id=device_id)
        if device_products:
            for device_product in device_products:
                product = dbapi.get_product(
                    product_id=device_product.product_id)
                info = {
                    'id': product.id,
                    'cat': product.cat,
                    'title': product.title,
                    'body': product.body,
                    'value': product.value,
                    'price': product.price,
                    'inventory': product.inventory,
                    'unit': device.product_unit
                }
                data.append(info)

    reply['data'] = data

    return make_response(jsonify(reply), status_code)
Пример #2
0
def get_products():
    dbg('get_products')
    reply, status_code = {'code': 0, 'msg': ''}, 200
    try:
        data = request.get_json()
        imei = data['imei']
    except:
        print_exception_info()
        raise ApiError('get products error', error.ERROR_PARAM)

    device = dbapi.get_device(imei=imei)
    if not device:
        raise ApiError('ERROR_DEVICE_NOT_FOUND', error.ERROR_DEVICE_NOT_FOUND)
    device_products = dbapi.get_device_product(device_id=device.id)
    data = []
    if device_products:
        for device_product in device_products:
            product = dbapi.get_product(product_id=device_product.product_id)
            if not product:
                continue
            dic = {
                'id': product.id,
                'title': product.title,
                'body': product.body,
                'value': product.value,
                'price': product.price,
                'unit': device.product_unit,
                'number':
                str(Fraction(product.value, device.product_unit_pluse)),
            }
            data.append(dic)
    reply['data'] = data

    return make_response(jsonify(reply), status_code)
Пример #3
0
def get_wallet_products():
    dbg('get_wallet_products')
    reply, status_code = {'code': 0, 'msg': ''}, 200
    try:
        data = request.get_json()
        imei = data['imei']
    except:
        print_exception_info()
        raise ApiError('get products error', error.ERROR_PARAM)

    device = dbapi.get_device(imei=imei)
    if not device:
        raise ApiError('ERROR_DEVICE_NOT_FOUND', error.ERROR_DEVICE_NOT_FOUND)

    agent_id = device.owner_agent_id

    products = dbapi.get_product(agent_id=agent_id, cat=99)
    data = []
    if products:
        for product in products:
            dic = {
                'id': product.id,
                'title': product.title,
                'body': product.body,
                'value': product.value,
                'price': product.price,
            }
            data.append(dic)
    reply['data'] = data

    return make_response(jsonify(reply), status_code)
Пример #4
0
def update_product():
    dbg('update_product')
    reply, status_code = {'code': 0, 'msg': ''}, 200

    try:
        data = request.get_json()
        product_id = data['product_id']
        update = data['update']
        keys = ('title', 'body', 'value', 'price')
        for k in update:
            assert (k in keys)
            if 'value' in update:
                assert (isinstance(update['value'], int)
                        and update['value'] > 0)
            if 'price' in update:
                assert (isinstance(update['price'], int)
                        and update['price'] > 0)
    except:
        print_exception_info()
        raise ApiError('update product error', error.ERROR_PARAM)

    product = dbapi.get_product(product_id=product_id)
    if not product:
        raise ApiError('update product', error.ERROR_PRODUCT_NOT_FOUND)
    product = dbapi.update_product(product, **update)
    db.session.add(product)
    db.session.commit()

    return make_response(jsonify(reply), status_code)
Пример #5
0
def make_pay():
    dbg('make_pay')
    reply, status_code = {'code': 0, 'msg': ''}, 200

    try:
        data = request.get_json()
        product_id = data['product_id']
        trade_type = data['trade_type']
        pay_mode = data['pay_mode']
        imei = data['imei']
        if pay_mode == 2:
            cur_url = data['url']
    except:
        print_exception_info()
        raise ApiError('pay error', error.ERROR_PARAM)

    device = dbapi.get_device(imei=imei)
    if not device:
        raise ApiError('ERROR_DEVICE_NOT_FOUND', error.ERROR_DEVICE_NOT_FOUND)

    agent_id = device.owner_agent_id

    user_id = g.oauth_user.user_id
    max_id = dbapi.get_max_pay_id()
    str_max_id = '%04d' % max_id
    if len(str_max_id) > 4:
        str_max_id = str_max_id[-4:]
    trade_no = str(pay_mode) + datetime.now().strftime(
        "%Y%m%d%H%M%S") + str_max_id
    product = dbapi.get_product(product_id=product_id)

    if pay_mode == 1:
        # 微信支付
        data = wechat_make_new_pay(product, trade_no, agent_id, user_id, imei,
                                   trade_type)
    elif pay_mode == 2:
        # 支付宝支付
        data = ali_make_new_pay(product, trade_no, agent_id, user_id, imei,
                                cur_url)
    elif pay_mode == 3:
        if product.cat == 99:
            raise ApiError('not support')
        # 钱包支付
        data = wallet_make_new_pay(product, trade_no, agent_id, user_id, imei)
    else:
        raise ApiError('ERROR_PAY', error.ERROR_PAY)

    reply['data'] = data

    return make_response(jsonify(reply), status_code)
Пример #6
0
def get_coupon():
    dbg('get_coupon')
    reply ,status_code = {'code': 0, 'msg': ''}, 200

    try:
        data = request.get_json()
        advertiser_id = data.get('advertiser_id')
        device_id = data.get('device_id')
    except:
        print_exception_info()
        raise ApiError('ERROR_PARAM', error.ERROR_PARAM)

    page  = request.args.get('page', 1, type=int)
    psize = request.args.get('psize', 10, type=int)

    data = []

    if advertiser_id:
        count, coupons = dbapi.get_coupon(advertiser_id=int(advertiser_id), page=page, psize=psize)
    elif device_id:
        count, coupons = dbapi.get_coupon(device_id=int(device_id), page=page, psize=psize)
    else:
        agent = dbapi.get_agent(user_id=current_user.id)
        if not agent:
            raise ApiError('ERROR_AGENT_NOT_FOUND', error.ERROR_AGENT_NOT_FOUND)
        agent_id = agent.id
        count, coupons = dbapi.get_coupon(agent_id=agent_id, page=page, psize=psize)

    if count:
        for coupon in coupons:
            product = dbapi.get_product(product_id=coupon.product_id)
            pay     = dbapi.get_pay(pay_id=coupon.pay_id)
            info = {
                'id': coupon.id,
                'title': coupon.title,
                'desc': coupon.desc,
                'img': url_for('static', filename=coupon.img),
                'total': coupon.total,
                'left': product.inventory,
                'pay_status': pay.status,
                'time': int(coupon.ctime.timestamp())
            }
            data.append(info)

    reply['data'] = {
        'count': count,
        'coupons': data
    }

    return make_response(jsonify(reply), status_code)
Пример #7
0
def manual_refund():
    dbg('manual_refund')
    reply ,status_code = {'code': 0, 'msg': ''}, 200
    try:
        data    = request.get_json()
        pay_id  = data['pay_id']
    except:
        print_exception_info()
        raise ApiError('ERROR_PARAM', error.ERROR_PARAM)

    pay = dbapi.get_pay(pay_id=pay_id)
    if not pay:
        raise ApiError('ERROR_PAY_NOT_FOUND', error.ERROR_PAY_NOT_FOUND)

    # 充值套餐、广告优惠券,不支持退款
    not_support_list = (99, 199)
    if pay.cat in not_support_list:
        raise ApiError('not support this', error.ERROR_AGENT_NO_PERMISSION)

    imei = pay.imei

    device = dbapi.get_device(imei=imei)
    if not device:
        raise ApiError('ERROR_DEVICE_NOT_FOUND', error.ERROR_DEVICE_NOT_FOUND)

    if device.owner_agent_id != current_user.agent_id:
        raise ApiError('ERROR_AGENT_NO_PERMISSION', error.ERROR_AGENT_NO_PERMISSION)

    refund_available = check_refund_available(device, pay.total_fee)
    if not refund_available:
        raise ApiError('ERROR_REFUND_NOT_AVAILABLE', error.ERROR_REFUND_NOT_AVAILABLE)

    if pay.status != 1:
        raise ApiError('ERROR_NOT_PAY', error.ERROR_NOT_PAY)

    product = dbapi.get_product(product_id=pay.product_id)
    if not product:
        raise ApiError('can not find product: %s' % pay.product_id)

    # 退款
    pay_refund(pay, product)

    db.session.commit()

    return make_response(jsonify(reply), status_code)
Пример #8
0
def random_get_coupon_receipt():
    dbg('random_get_coupon_receipt')
    reply, status_code = {'code': 0, 'msg': ''}, 200

    try:
        data = request.get_json()
        imei = data['imei']
    except:
        print_exception_info()
        raise ApiError('get machine record error', error.ERROR_PARAM)

    device = dbapi.get_device(imei=imei)
    if not device:
        raise ApiError('ERROR_DEVICE_NOT_FOUND', error.ERROR_DEVICE_NOT_FOUND)

    coupons = dbapi.get_coupon(device_id=device.id, paid=1, inventory=1)
    if coupons:
        coupon = random.choice(coupons)
        coupon_id = coupon.id
        code = gen_coupon_receipt_code(coupon_id, coupon.prefix)
        user_id = g.oauth_user.user_id
        coupon_receipt = dbapi.make_new_coupon_receipt(coupon_id, user_id,
                                                       code)
        product = dbapi.get_product(product_id=coupon.product_id)
        if product.inventory <= 0:
            raise ApiError('ERROR_COUPON_NO_AVAILABLE',
                           error.ERROR_COUPON_NO_AVAILABLE)
        product = dbapi.update_product(product,
                                       inventory=product.inventory - 1)
        color = get_boxed_reverse_color(coupon.img)
        reply['data'] = {
            'img': url_for('static', filename=coupon.img),
            'code': code,
            'color': color
        }
    else:
        raise ApiError('ERROR_COUPON_NO_AVAILABLE',
                       error.ERROR_COUPON_NO_AVAILABLE)

    db.session.commit()

    return make_response(jsonify(reply), status_code)
Пример #9
0
def delete_product():
    dbg('delete_product')
    reply, status_code = {'code': 0, 'msg': ''}, 200

    try:
        data = request.get_json()
        product_id = data['product_id']
    except:
        print_exception_info()
        raise ApiError('delete product error', error.ERROR_PARAM)

    product = dbapi.get_product(product_id=product_id)
    if not product:
        raise ApiError('update product', error.ERROR_PRODUCT_NOT_FOUND)

    product = dbapi.update_product(product, deleted=1)
    db.session.add(product)
    db.session.commit()

    return make_response(jsonify(reply), status_code)
Пример #10
0
def pay_coupon():
    dbg('pay_coupon')
    reply ,status_code = {'code': 0, 'msg': ''}, 200

    try:
        data = request.get_json()
        coupon_id = data['coupon_id']
    except:
        print_exception_info()
        raise ApiError('ERROR_PARAM', error.ERROR_PARAM)

    coupon = dbapi.get_coupon(id=coupon_id)
    if not coupon:
        raise ApiError('ERROR_COUPON_NOT_FOUND', error.ERROR_COUPON_NOT_FOUND)

    pay    = dbapi.get_pay(pay_id=coupon.pay_id)
    if not pay:
        raise ApiError('ERROR_PAY_NOT_FOUND', error.ERROR_PAY_NOT_FOUND)

    if pay.status != 0 or coupon.paid:
        raise ApiError('ERROR_ALREADY_PAID', error.ERROR_ALREADY_PAID)

    if int(datetime.now().timestamp()) - int(pay.utime.timestamp()) >= 2*60*60:
        product = dbapi.get_product(product_id=coupon.product_id)
        trade_no = pay.trade_no
        pay = wechat_qrcode_update(pay, product, trade_no, current_user.id)

    reply['data'] = {
        'pay_request': {
            'prepay_id': pay.prepay_id,
            'qrcode': pay.qrcode
        },
        'trade_no'   : pay.trade_no,
        'id'         : pay.id
    }

    return make_response(jsonify(reply), status_code)
Пример #11
0
def machine_start():
    dbg('machine_start')
    reply, status_code = {'code': 0, 'msg': ''}, 200

    try:
        data = request.get_json()
        cat = data['cat']
        pay_id = data['pay_id']

    except:
        print_exception_info()
        raise ApiError('ERROR_PARAM', error.ERROR_PARAM)

    pay = dbapi.get_pay(pay_id=pay_id)
    if not pay:
        raise ApiError('machine start error', error.ERROR_PAY_NOT_FOUND)

    imei = pay.imei

    if pay.status != 1:
        raise ApiError('machine start error', error.ERROR_NOT_PAY)

    product = dbapi.get_product(product_id=pay.product_id)
    if not product:
        raise ApiError('can not find product: %s' % pay.product_id)

    if product.cat == 99:
        raise ApiError('ERROR_PAY_NOT_FOUND', error.ERROR_PAY_NOT_FOUND)

    if product.cat == 0:
        # 倒计时限制同时支付
        last_pay = dbapi.get_last_pay(pay.imei, not_include_pay_id=pay_id)
        if last_pay and datetime.now().timestamp() - last_pay.utime.timestamp(
        ) < 5:
            # 退款
            pay_refund(pay, product)
            raise ApiError('ERROR_PAY_TOO_FREQUENCE',
                           error.ERROR_PAY_TOO_FREQUENCE)

    dbg('cat: %s' % cat)
    device = dbapi.get_device(imei=imei)
    if not device:
        raise ApiError('ERROR_DEVICE_NOT_FOUND', error.ERROR_DEVICE_NOT_FOUND)

    value = product.value
    record = dbapi.get_record(pay_id=pay.id)
    if record:
        raise ApiError('machine start error', error.ERROR_ALREADY_START)

    high = device.high
    low = device.low
    cat = product.cat
    dbg('imei: %s, value: %d, cat: %d, high: %d, low: %d' %
        (imei, value, cat, low, high))

    cat = product.cat
    if cat in (0, 2, 3):
        device_type = device.cat
        succ, result = launch_relay_signal_deivce_v2(imei, value, device_type)

    elif cat == 1:
        if imei == '868575023189139' and value == 3:
            succ, result = launch_pulse_signal_deivce(imei, 2, high, low)
            time.sleep(2)
            succ, result = launch_pulse_signal_deivce(imei, 1, high, low)
        else:
            succ, result = launch_pulse_signal_deivce(imei, value, high, low)

    else:
        raise ApiError('not support')

    if not succ:
        # 退款
        pay_refund(pay, product)

        try:
            data = json.loads(result)
            dbg((data['code'], data['msg']))
            reply['code'] = data['code']
            reply['msg'] = data['msg']
            status_code = 422
        except:
            print_exception_info()
            reply['code'] = 99
            reply['msg'] = 'server error'
            status_code = 500
        return make_response(jsonify(reply), status_code)

    if cat == 0:
        # 按摩椅需要记录开始记录
        pay_way = pay.pay_mode
        stime = datetime.now()
        etime = stime + timedelta(seconds=product.value)
        record = dbapi.make_new_record(pay.id, pay_way, pay.user_id,
                                       product.agent_id, pay.product_id, stime,
                                       etime)

    else:
        # 投币器也需要记录开始记录
        pay_way = pay.pay_mode
        stime = datetime.now()
        etime = stime
        record = dbapi.make_new_record(pay.id, pay_way, pay.user_id,
                                       product.agent_id, pay.product_id, stime,
                                       etime)

    db.session.commit()

    reply['data'] = {
        'id': record.id,
        'stime': int(record.stime.timestamp()),
        'etime': int(record.etime.timestamp()),
        'now': int(time.time()),
        'user_id': record.user_id,
    }

    return make_response(jsonify(reply), status_code)
Пример #12
0
def ali_notify():
    dbg('ali_notify')

    reply = {"return_code": 'SUCCESS', "return_msg": ""}

    try:
        trade_no = request.form['out_trade_no']
        nofity_res = {}
        for k in request.form:
            print(k, request.form[k])
            nofity_res[k] = request.form[k]
        trade_status = request.form['trade_status']
        ali_trade_no = request.form['trade_no']
        buyer_id = request.form['buyer_id']
        buyer_logon_id = request.form['buyer_logon_id']
        cash_fee = request.form.get(
            'buyer_pay_amount') or request.form['total_amount']
    except:
        print_exception_info()
        raise ApiError('ERROR_PARAM', error.ERROR_PARAM)

    # 检查订单
    pay = dbapi.get_pay(trade_no=trade_no)
    if not pay:
        raise ApiError('can not find pay: %s' % trade_no)

    # 签名
    # sign = request.form['sign']
    # ali_config = dbapi.get_ali_config(agent_id=int(agent_id))
    # key_path   = ali_config.pub_path

    # 如果已经支付,则直接返回Ok
    if pay.status > 0:
        return make_response('success')

    if trade_status == 'TRADE_CLOSED':
        dbapi.update_pay(pay,
                         user_id=pay.user_id,
                         status=2,
                         nofity_res=json.dumps(nofity_res))
        try:
            db.session.commit()
        except:
            print_exception_info()
            db.session.rollback()
            raise ApiError('ali_notify error')

    elif trade_status == 'TRADE_SUCCESS':
        dbapi.update_pay(pay=pay,
                         user_id=pay.user_id,
                         status=1,
                         cash_fee=cash_fee,
                         nofity_res=json.dumps(nofity_res),
                         ali_trade_no=ali_trade_no)
        product = dbapi.get_product(product_id=pay.product_id)
        if product.cat == 99:
            # 钱包充值
            user_id = pay.user_id
            wallet = dbapi.get_wallet(role=0,
                                      user_id=user_id,
                                      agent_id=pay.agent_id)
            wallet_id = wallet.id
            trade_type = dbapi.WALLET_TRADE_TYPE_DEPOSIT
            receipt = product.value
            withdrawable_receipt = 0
            remark = product.title
            wallet_receipt = dbapi.make_new_wallet_receipt(
                user_id, pay.agent_id, wallet_id, trade_type, receipt,
                withdrawable_receipt, remark)

            balance = wallet.balance + receipt
            wallet = dbapi.update_wallet(wallet, balance=balance)

        wechat_pay_receipt(pay)

        try:
            db.session.commit()
        except:
            print_exception_info()
            db.session.rollback()
            raise ApiError('ali_notify error', error.ERROR_DATABASE_COMMIT)

    return make_response('success')
Пример #13
0
def pay_notify():
    dbg('pay_notify')
    reply = {"return_code": 'SUCCESS', "return_msg": ""}

    try:
        data_info = request.data.decode('utf8')
        data = wechatpay.xml_to_dict(data_info)
        nofity_res = json.dumps(data)
        dbg('data_info: %s' % data_info)

        return_code = None
        result_code = None

        if "result_code" in data and "return_code" in data:
            return_code = data["return_code"]
            result_code = data["result_code"]

        if return_code != "SUCCESS":
            raise ApiError('wechat interface return error')

        # return_code为`SUCCESS`, 则包含out_trade_no

        # 检查订单
        trade_no = data['out_trade_no']
        pay = dbapi.get_pay(trade_no=trade_no)
        if not pay:
            raise ApiError('can not find pay: %s' % trade_no)

        # 如果已经支付,则直接返回Ok
        if pay.status > 0:
            return make_response(wechatpay.dict_to_xml(reply).encode('utf-8'))

        # 检查签名
        sign = data['sign']
        data.pop('sign')
        wechat_config = dbapi.get_wechat_config(agent_id=pay.agent_id)
        key = wechat_config.mchkey
        local_sign = wechatpay.params_sign(data, key)
        data['sign'] = sign
        dbg((sign, local_sign))
        if sign != local_sign:
            raise ApiError('sign error')

        if result_code != "SUCCESS":
            '''
                ``` 支付失败, 更新支付异常
            '''
            dbapi.update_pay(pay, status=2, nofity_res=nofity_res)

            try:
                db.session.commit()
            except:
                print_exception_info()
                db.session.rollback()
                raise ApiError('pay_notify error')

        else:
            '''
                ``` 支付成功, 并更新支付成功
            '''
            cash_fee = data['cash_fee']
            dbapi.update_pay(pay=pay,
                             status=1,
                             cash_fee=cash_fee,
                             nofity_res=nofity_res)
            product = dbapi.get_product(product_id=pay.product_id)
            if product.cat == 99:
                # 钱包充值
                user_id = pay.user_id
                wallet = dbapi.get_wallet(role=0,
                                          user_id=user_id,
                                          agent_id=pay.agent_id)
                wallet_id = wallet.id
                trade_type = dbapi.WALLET_TRADE_TYPE_DEPOSIT
                receipt = product.value
                withdrawable_receipt = 0
                remark = product.title
                wallet_receipt = dbapi.make_new_wallet_receipt(
                    user_id, pay.agent_id, wallet_id, trade_type, receipt,
                    withdrawable_receipt, remark)

                balance = wallet.balance + receipt
                wallet = dbapi.update_wallet(wallet, balance=balance)

            if product.cat == dbapi.PRODUCT_CAT_COUPON:
                # 优惠券
                coupon = dbapi.get_coupon(pay_id=pay.id)
                if coupon:
                    coupon = dbapi.update_coupon(coupon, paid=1)

            wechat_pay_receipt(pay)

            try:
                db.session.commit()
            except:
                print_exception_info()
                db.session.rollback()
                raise ApiError('wechat_pay_notify error',
                               error.ERROR_DATABASE_COMMIT)

    except ApiError as e:
        # if e.msg != 'wechat pay failed':
        print_exception_info()
        reply['return_code'] = "FAIL"
        reply['return_msg'] = e.msg
    except:
        print_exception_info()
        reply['return_code'] = "FAIL"
        reply['return_msg'] = 'server error'

    res_data = wechatpay.dict_to_xml(reply).encode('utf-8')
    print(res_data)
    return make_response(res_data)