zoukankan      html  css  js  c++  java
  • Python实现ATM+购物商城

    需求:

    模拟实现一个ATM + 购物商城程序
        额度 15000或自定义
        实现购物商城,买东西加入 购物车,调用信用卡接口结账
        可以提现,手续费5%
        每月22号出账单,每月10号为还款日,过期未还,按欠款总额 万分之5 每日计息
        支持多账户登录
        支持账户间转账
        记录每月日常消费流水
        提供还款接口
        ATM记录操作日志 
        提供管理接口,包括添加账户、用户额度,冻结账户等。。。
        用户认证用装饰器
    
    实现功能:
        额度 15000或自定义
        实现购物商城,买东西加入 购物车,调用信用卡接口结账
        可以提现,手续费5%
        支持多账户登录
        记录每月日常消费流水
        提供还款接口
        ATM记录操作日志 
        提供管理接口,包括添加账户、用户额度,冻结账户等。。。
        用户认证用装饰器
    

    程序结构:

    atm/
    ├── README
    └── atm #ATM主程目录
       ├── __init__.py
       ├── bin #ATM 执行文件 目录
       │   ├── __init__.py
       │   ├── atm.py  #ATM 执行程序
       │   └── manage.py #ATM 管理端,未实现
       ├── conf #配置文件
       │   ├── __init__.py
       │   └── settings.py
       ├── core #主要程序逻辑都 在这个目录 里
       │   ├── __init__.py
       │   ├── accounts.py  #用于从文件里加载和存储账户数据
       │   ├── auth.py      #用户认证模块
       │   ├── db_handler.py   #数据库连接引擎
       │   ├── logger.py       #日志记录模块
       │   ├── main.py         #主逻辑交互程序
       │   └── transaction.py  #记账还钱取钱等所有的与账户金额相关的操作都 在这
       ├── db  #用户数据存储的地方
       │   ├── __init__.py
       │   ├── account_sample.py #生成一个初始的账户数据 ,把这个数据 存成一个 以这个账户id为文件名的文件,放在accounts目录 就行了,程序自己去会这里找
       │   └── accounts #存各个用户的账户数据 ,一个用户一个文件
       │       └── 1234.json #一个用户账户示例文件
       └── log #日志目录
           ├── __init__.py
           ├── access.log #用户访问和操作的相关日志
           └── transactions.log    #所有的交易日志

    二、流程图

    三、代码

     bin/atm.py

    #!/usr/bin/env python
    # -*- coding: utf-8 -*-

    import os
    import sys
    base_dir = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
    print(base_dir)
    sys.path.append(base_dir)

    from core import main

    if __name__ == '__main__':
    main.run()

     

     conf/settings.py

    #!/usr/bin/env python
    # -*- coding: utf-8 -*-
    import os
    import sys
    import logging
    BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))


    DATABASE = {
    'engine': 'file_storage', #support mysql,postgresql in the future
    'name':'accounts',
    'path': "%s/db" % BASE_DIR
    }


    LOG_LEVEL = logging.INFO
    LOG_TYPES = {
    'transaction': 'transactions.log',
    'access': 'access.log',
    }

    TRANSACTION_TYPE = {
    'repay':{'action':'plus', 'interest':0.03},
    'withdraw':{'action':'minus', 'interest':0.05},
    'transfer':{'action':'minus', 'interest':0.05},
    'consume':{'action':'minus', 'interest':0},

    }


    复制代码
     1 #!/usr/bin/env python
     2 # -*- coding: utf-8 -*-
     3 import os
     4 import sys
     5 import logging
     6 BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
     7 
     8 
     9 DATABASE = {
    10     'engine': 'file_storage', #support mysql,postgresql in the future
    11     'name':'accounts',
    12     'path': "%s/db" % BASE_DIR
    13 }
    14 
    15 
    16 LOG_LEVEL = logging.INFO
    17 LOG_TYPES = {
    18     'transaction': 'transactions.log',
    19     'access': 'access.log',
    20 }
    21 
    22 TRANSACTION_TYPE = {
    23     'repay':{'action':'plus', 'interest':0.03},
    24     'withdraw':{'action':'minus', 'interest':0.05},
    25     'transfer':{'action':'minus', 'interest':0.05},
    26     'consume':{'action':'minus', 'interest':0},
    27 
    28 }
    复制代码

     core/main.py

    #!/usr/bin/env python
    # -*- coding: utf-8 -*-

    '''
    main program handle module , handle all the user interaction stuff

    '''

    from core import auth
    from core import accounts
    from core import logger
    from core import accounts
    from core import transaction
    from core.auth import login_required
    import time

    #transaction logger
    trans_logger = logger.logger('transaction')
    #access logger
    access_logger = logger.logger('access')


    #temp account data ,only saves the data in memory
    user_data = {
    'account_id':None,
    'is_authenticated':False,
    'account_data':None

    }

    def account_info(acc_data):
    account_data = accounts.load_current_balance(acc_data['account_id'])
    data_info = u'''
    33[34;1m 账号ID:%s
    余额: %s
    信用度:%s
    账号注册时间:%s
    账号过期时间:%s
    工资天数:%s
    33[0m'''%(acc_data['account_id'],
    account_data['balance'],
    account_data['credit'],
    account_data['enroll_date'],
    account_data['expire_date'],
    account_data['pay_day'],)
    print(data_info)


    @login_required
    def repay(acc_data):
    '''
    print current balance and let user repay the bill
    :return:
    '''
    account_data = accounts.load_current_balance(acc_data['account_id'])
    #再从硬盘加载一次数据, 为了确保数据是最新的
    #for k,v in account_data.items():
    # print(k,v )
    current_balance= ''' --------- BALANCE INFO --------
    Credit : %s
    Balance: %s''' %(account_data['credit'],account_data['balance'])
    print(current_balance)
    back_flag = False
    while not back_flag:
    repay_amount = input("33[33;1mInput repay amount:33[0m").strip()
    if len(repay_amount) >0 and repay_amount.isdigit():
    #print('ddd 00')
    new_balance = transaction.make_transaction(trans_logger,account_data,'repay', repay_amount)
    if new_balance:
    print('''33[42;1mNew Balance:%s33[0m''' %(new_balance['balance']))

    else:
    print('33[31;1m[%s] is not a valid amount, only accept integer!33[0m' % repay_amount)

    if repay_amount == 'b':
    back_flag = True
    def withdraw(acc_data):
    '''
    print current balance and let user do the withdraw action
    :param acc_data:
    :return:
    '''
    account_data = accounts.load_current_balance(acc_data['account_id'])
    current_balance= ''' --------- BALANCE INFO --------
    Credit : %s
    Balance: %s''' %(account_data['credit'],account_data['balance'])
    print(current_balance)
    back_flag = False
    while not back_flag:
    withdraw_amount = input("33[33;1mInput withdraw amount:33[0m").strip()
    if len(withdraw_amount) >0 and withdraw_amount.isdigit():
    new_balance = transaction.make_transaction(trans_logger,account_data,'withdraw', withdraw_amount)
    if new_balance:
    print('''33[42;1mNew Balance:%s33[0m''' %(new_balance['balance']))

    else:
    print('33[31;1m[%s] is not a valid amount, only accept integer!33[0m' % withdraw_amount)

    if withdraw_amount == 'b':
    back_flag = True

    def transfer(acc_data):
    pass
    def pay_check(acc_data):
    pass
    def logout(acc_data):
    exit()


    def shopping(acc_data):
    '''

    :param acc_data:
    :return:
    '''
    product_list = [
    ['Iphone7 Plus', 6500],
    ['Iphone8 ', 8200],
    ['MacBook Pro', 12000],
    ['Python Book', 99],
    ['Coffee', 33],
    ['Bike', 666],
    ['pen', 2]
    ]
    shopping_cart = []
    count = 0
    salary = acc_data['account_data']['balance']
    while True:
    account_data = accounts.load_current_balance(acc_data['account_id'])
    print(">> 欢迎来到电子商城 您的余额是 %s 元<<" % (salary))
    for index, i in enumerate(product_list): # 循环商品列表,商品列表索引
    print("%s. %s %s" % (index, i[0], i[1])) # 打印商品列表,显示商品列表索引
    choice = input(">>请输入商品序号或输入 exit 退出商城>>: ").strip()
    if len(choice) == 0: # 判断输入字符串是否为空和字符串长度
    print('-->您没有选择商品<--')
    continue
    if choice.isdigit(): # 判断输入的choice是不是一个数字
    choice = int(choice) # 把输入的字符串转成整型
    if choice < len(product_list) and choice >= 0: # 输入的整数必须小于商品列表的数量
    product_item = product_list[choice] # 获取商品
    if salary >= product_item[1]: # 拿现有金额跟商品对比,是否买得起
    salary -= product_item[1] # 扣完商品的价格
    shopping_cart.append(product_item) # 把选着的商品加入购物车
    print("添加 33[32;1m%s33[0m 到购物车,您目前的金额是
    33[31;1m%s33[0m" % (product_item[0], salary))
    else:
    print("对不起,您的金额不足,还差 33[31;1m%s33[0m" % (product_item[1] - salary,))
    else:
    print("-->没有此商品<--")
    elif choice == "exit":
    total_cost = 0
    print("您的购物车列表:")
    for i in shopping_cart:
    print(i)
    total_cost += i[1]
    print("您的购物车总价是: 33[31;1m%s33[0m" % (total_cost,))
    print("您目前的余额是: 33[31;1m%s33[0m" % (salary,))
    new_balance = transaction.make_transaction(trans_logger, account_data, 'withdraw', total_cost)
    if new_balance:
    print('''33[42;1mNew Balance:%s33[0m''' % (new_balance['balance']))
    break


    def interactive(acc_data):
    '''
    interact with user
    :return:
    '''
    menu = u'''
    ------- hehe Bank ---------
    33[32;1m
    1. 账户信息(实现)
    2. 还款(实现)
    3. 取款(实现)
    4. 转账
    5. 账单
    6. 商城(实现)
    7. 退出(实现)
    33[0m'''
    menu_dic = {
    '1': account_info,
    '2': repay,
    '3': withdraw,
    '4': transfer,
    '5': pay_check,
    '6': shopping,
    '7': logout,
    }
    exit_flag = False
    while not exit_flag:
    print(menu)
    user_option = input(">>:").strip()
    if user_option in menu_dic:
    #print('accdata',acc_data)
    #acc_data['is_authenticated'] =False
    menu_dic[user_option](acc_data)

    else:
    print("33[31;1mOption does not exist!33[0m")
    def run():
    '''
    this function will be called right a way when the program started, here handles the user interaction stuff
    :return:
    '''
    acc_data = auth.acc_login(user_data,access_logger)
    if user_data['is_authenticated']:
    user_data['account_data'] = acc_data
    interactive(user_data)


    复制代码
      1 #!/usr/bin/env python
      2 # -*- coding: utf-8 -*-
      3 
      4 '''
      5 main program handle module , handle all the user interaction stuff
      6 
      7 '''
      8 
      9 from core import auth
     10 from core import accounts
     11 from core import logger
     12 from core import accounts
     13 from core import transaction
     14 from core.auth import login_required
     15 import time
     16 
     17 #transaction logger
     18 trans_logger = logger.logger('transaction')
     19 #access logger
     20 access_logger = logger.logger('access')
     21 
     22 
     23 #temp account data ,only saves the data in memory
     24 user_data = {
     25     'account_id':None,
     26     'is_authenticated':False,
     27     'account_data':None
     28 
     29 }
     30 
     31 def account_info(acc_data):
     32     account_data = accounts.load_current_balance(acc_data['account_id'])
     33     data_info = u'''
     34     33[34;1m 账号ID:%s
     35     余额:  %s
     36     信用度:%s
     37     账号注册时间:%s
     38     账号过期时间:%s
     39     工资天数:%s
     40     33[0m'''%(acc_data['account_id'],
     41                 account_data['balance'],
     42                 account_data['credit'],
     43                 account_data['enroll_date'],
     44                 account_data['expire_date'],
     45                 account_data['pay_day'],)
     46     print(data_info)
     47 
     48 
     49 @login_required
     50 def repay(acc_data):
     51     '''
     52     print current balance and let user repay the bill
     53     :return:
     54     '''
     55     account_data = accounts.load_current_balance(acc_data['account_id'])
     56     #再从硬盘加载一次数据, 为了确保数据是最新的
     57     #for k,v in account_data.items():
     58     #    print(k,v )
     59     current_balance= ''' --------- BALANCE INFO --------
     60         Credit :    %s
     61         Balance:    %s''' %(account_data['credit'],account_data['balance'])
     62     print(current_balance)
     63     back_flag = False
     64     while not back_flag:
     65         repay_amount = input("33[33;1mInput repay amount:33[0m").strip()
     66         if len(repay_amount) >0 and repay_amount.isdigit():
     67             #print('ddd 00')
     68             new_balance = transaction.make_transaction(trans_logger,account_data,'repay', repay_amount)
     69             if new_balance:
     70                 print('''33[42;1mNew Balance:%s33[0m''' %(new_balance['balance']))
     71 
     72         else:
     73             print('33[31;1m[%s] is not a valid amount, only accept integer!33[0m' % repay_amount)
     74 
     75         if repay_amount == 'b':
     76             back_flag = True
     77 def withdraw(acc_data):
     78     '''
     79     print current balance and let user do the withdraw action
     80     :param acc_data:
     81     :return:
     82     '''
     83     account_data = accounts.load_current_balance(acc_data['account_id'])
     84     current_balance= ''' --------- BALANCE INFO --------
     85         Credit :    %s
     86         Balance:    %s''' %(account_data['credit'],account_data['balance'])
     87     print(current_balance)
     88     back_flag = False
     89     while not back_flag:
     90         withdraw_amount = input("33[33;1mInput withdraw amount:33[0m").strip()
     91         if len(withdraw_amount) >0 and withdraw_amount.isdigit():
     92             new_balance = transaction.make_transaction(trans_logger,account_data,'withdraw', withdraw_amount)
     93             if new_balance:
     94                 print('''33[42;1mNew Balance:%s33[0m''' %(new_balance['balance']))
     95 
     96         else:
     97             print('33[31;1m[%s] is not a valid amount, only accept integer!33[0m' % withdraw_amount)
     98 
     99         if withdraw_amount == 'b':
    100             back_flag = True
    101 
    102 def transfer(acc_data):
    103     pass
    104 def pay_check(acc_data):
    105     pass
    106 def logout(acc_data):
    107     exit()
    108 
    109 
    110 def shopping(acc_data):
    111     '''
    112 
    113     :param acc_data:
    114     :return:
    115     '''
    116     product_list = [
    117         ['Iphone7 Plus', 6500],
    118         ['Iphone8 ', 8200],
    119         ['MacBook Pro', 12000],
    120         ['Python Book', 99],
    121         ['Coffee', 33],
    122         ['Bike', 666],
    123         ['pen', 2]
    124     ]
    125     shopping_cart = []
    126     count = 0
    127     salary = acc_data['account_data']['balance']
    128     while True:
    129         account_data = accounts.load_current_balance(acc_data['account_id'])
    130         print(">> 欢迎来到电子商城 您的余额是 %s 元<<" % (salary))
    131         for index, i in enumerate(product_list):  # 循环商品列表,商品列表索引
    132             print("%s.	%s	%s" % (index, i[0], i[1]))  # 打印商品列表,显示商品列表索引
    133         choice = input(">>请输入商品序号或输入 exit 退出商城>>: ").strip()
    134         if len(choice) == 0:  # 判断输入字符串是否为空和字符串长度
    135             print('-->您没有选择商品<--')
    136             continue
    137         if choice.isdigit():  # 判断输入的choice是不是一个数字
    138             choice = int(choice)  # 把输入的字符串转成整型
    139             if choice < len(product_list) and choice >= 0:  # 输入的整数必须小于商品列表的数量
    140                 product_item = product_list[choice]  # 获取商品
    141                 if salary >= product_item[1]:  # 拿现有金额跟商品对比,是否买得起
    142                     salary -= product_item[1]  # 扣完商品的价格
    143                     shopping_cart.append(product_item)  # 把选着的商品加入购物车
    144                     print("添加 33[32;1m%s33[0m 到购物车,您目前的金额是 
    145     33[31;1m%s33[0m" % (product_item[0], salary))
    146                 else:
    147                     print("对不起,您的金额不足,还差 33[31;1m%s33[0m" % (product_item[1] - salary,))
    148             else:
    149                 print("-->没有此商品<--")
    150         elif choice == "exit":
    151             total_cost = 0
    152             print("您的购物车列表:")
    153             for i in shopping_cart:
    154                 print(i)
    155                 total_cost += i[1]
    156             print("您的购物车总价是: 33[31;1m%s33[0m" % (total_cost,))
    157             print("您目前的余额是: 33[31;1m%s33[0m" % (salary,))
    158             new_balance = transaction.make_transaction(trans_logger, account_data, 'withdraw', total_cost)
    159             if new_balance:
    160                 print('''33[42;1mNew Balance:%s33[0m''' % (new_balance['balance']))
    161             break
    162 
    163 
    164 def interactive(acc_data):
    165     '''
    166     interact with user
    167     :return:
    168     '''
    169     menu = u'''
    170     ------- hehe Bank ---------
    171     33[32;1m
    172     1.  账户信息(实现)
    173     2.  还款(实现)
    174     3.  取款(实现)
    175     4.  转账
    176     5.  账单
    177     6.  商城(实现)
    178     7.  退出(实现)
    179     33[0m'''
    180     menu_dic = {
    181         '1': account_info,
    182         '2': repay,
    183         '3': withdraw,
    184         '4': transfer,
    185         '5': pay_check,
    186         '6': shopping,
    187         '7': logout,
    188     }
    189     exit_flag = False
    190     while not exit_flag:
    191         print(menu)
    192         user_option = input(">>:").strip()
    193         if user_option in menu_dic:
    194             #print('accdata',acc_data)
    195             #acc_data['is_authenticated'] =False
    196             menu_dic[user_option](acc_data)
    197 
    198         else:
    199             print("33[31;1mOption does not exist!33[0m")
    200 def run():
    201     '''
    202     this function will be called right a way when the program started, here handles the user interaction stuff
    203     :return:
    204     '''
    205     acc_data = auth.acc_login(user_data,access_logger)
    206     if user_data['is_authenticated']:
    207         user_data['account_data'] = acc_data
    208         interactive(user_data)
    复制代码

    core/transaction.py

    #!/usr/bin/env python
    # -*- coding: utf-8 -*-

    from conf import settings
    from core import accounts
    from core import logger
    #transaction logger

    def make_transaction(log_obj,account_data,tran_type,amount,**others):
    '''
    deal all the user transactions
    :param account_data: user account data
    :param tran_type: transaction type
    :param amount: transaction amount
    :param others: mainly for logging usage
    :return:
    '''
    amount = float(amount)
    if tran_type in settings.TRANSACTION_TYPE:

    interest = amount * settings.TRANSACTION_TYPE[tran_type]['interest']
    old_balance = account_data['balance']
    if settings.TRANSACTION_TYPE[tran_type]['action'] == 'plus':
    new_balance = old_balance + amount + interest
    elif settings.TRANSACTION_TYPE[tran_type]['action'] == 'minus':
    new_balance = old_balance - amount - interest
    #check credit
    if new_balance <0:
    print('''33[31;1mYour credit [%s] is not enough for this transaction [-%s], your current balance is
    [%s]''' %(account_data['credit'],(amount + interest), old_balance ))
    return
    account_data['balance'] = new_balance
    accounts.dump_account(account_data) #save the new balance back to file
    log_obj.info("account:%s action:%s amount:%s interest:%s" %
    (account_data['id'], tran_type, amount,interest) )
    return account_data
    else:
    print("33[31;1mTransaction type [%s] is not exist!33[0m" % tran_type)


    复制代码
     1 #!/usr/bin/env python
     2 # -*- coding: utf-8 -*-
     3 
     4 from conf import settings
     5 from core import accounts
     6 from core import logger
     7 #transaction logger
     8 
     9 
    10 
    11 def make_transaction(log_obj,account_data,tran_type,amount,**others):
    12     '''
    13     deal all the user transactions
    14     :param account_data: user account data
    15     :param tran_type: transaction type
    16     :param amount: transaction amount
    17     :param others: mainly for logging usage
    18     :return:
    19     '''
    20     amount = float(amount)
    21     if tran_type in  settings.TRANSACTION_TYPE:
    22 
    23         interest =  amount * settings.TRANSACTION_TYPE[tran_type]['interest']
    24         old_balance = account_data['balance']
    25         if settings.TRANSACTION_TYPE[tran_type]['action'] == 'plus':
    26             new_balance = old_balance + amount + interest
    27         elif settings.TRANSACTION_TYPE[tran_type]['action'] == 'minus':
    28             new_balance = old_balance - amount - interest
    29             #check credit
    30             if  new_balance <0:
    31                 print('''33[31;1mYour credit [%s] is not enough for this transaction [-%s], your current balance is
    32                 [%s]''' %(account_data['credit'],(amount + interest), old_balance ))
    33                 return
    34         account_data['balance'] = new_balance
    35         accounts.dump_account(account_data) #save the new balance back to file
    36         log_obj.info("account:%s   action:%s    amount:%s   interest:%s" %
    37                           (account_data['id'], tran_type, amount,interest) )
    38         return account_data
    39     else:
    40         print("33[31;1mTransaction type [%s] is not exist!33[0m" % tran_type)
    复制代码

    core/accounts.py

    #!/usr/bin/env python
    # -*- coding: utf-8 -*-

    import json
    import time
    from core import db_handler
    from conf import settings


    def load_current_balance(account_id):
    '''
    return account balance and other basic info
    :param account_id:
    :return:
    '''
    # db_path = db_handler.db_handler(settings.DATABASE)
    # account_file = "%s/%s.json" %(db_path,account_id)
    #
    db_api = db_handler.db_handler()
    data = db_api("select * from accounts where account=%s" % account_id)

    return data

    # with open(account_file) as f:
    # acc_data = json.load(f)
    # return acc_data
    def dump_account(account_data):
    '''
    after updated transaction or account data , dump it back to file db
    :param account_data:
    :return:
    '''
    db_api = db_handler.db_handler()
    data = db_api("update accounts where account=%s" % account_data['id'],account_data=account_data)

    # db_path = db_handler.db_handler(settings.DATABASE)
    # account_file = "%s/%s.json" %(db_path,account_data['id'])
    # with open(account_file, 'w') as f:
    # acc_data = json.dump(account_data,f)

    return True


    复制代码
     1 #!/usr/bin/env python
     2 # -*- coding: utf-8 -*-
     3 
     4 import json
     5 import time
     6 from core import db_handler
     7 from conf import settings
     8 
     9 
    10 def load_current_balance(account_id):
    11     '''
    12     return account balance and other basic info
    13     :param account_id:
    14     :return:
    15     '''
    16     # db_path = db_handler.db_handler(settings.DATABASE)
    17     # account_file = "%s/%s.json" %(db_path,account_id)
    18     #
    19     db_api = db_handler.db_handler()
    20     data = db_api("select * from accounts where account=%s" % account_id)
    21 
    22     return data
    23 
    24     # with open(account_file) as f:
    25     #     acc_data = json.load(f)
    26     #     return  acc_data
    27 def dump_account(account_data):
    28     '''
    29     after updated transaction or account data , dump it back to file db
    30     :param account_data:
    31     :return:
    32     '''
    33     db_api = db_handler.db_handler()
    34     data = db_api("update accounts where account=%s" % account_data['id'],account_data=account_data)
    35 
    36     # db_path = db_handler.db_handler(settings.DATABASE)
    37     # account_file = "%s/%s.json" %(db_path,account_data['id'])
    38     # with open(account_file, 'w') as f:
    39     #     acc_data = json.dump(account_data,f)
    40 
    41     return True
    复制代码

    core/auth.py

    #!/usr/bin/env python
    # -*- coding: utf-8 -*-
    import os
    from core import db_handler
    from conf import settings
    from core import logger
    import json
    import time

    def login_required(func):
    "验证用户是否登录"

    def wrapper(*args,**kwargs):
    #print('--wrapper--->',args,kwargs)
    if args[0].get('is_authenticated'):
    return func(*args,**kwargs)
    else:
    exit("User is not authenticated.")
    return wrapper


    def acc_auth(account,password):
    '''
    account auth func
    :param account: credit account number
    :param password: credit card password
    :return: if passed the authentication , retun the account object, otherwise ,return None
    '''
    db_path = db_handler.db_handler(settings.DATABASE)
    account_file = "%s/%s.json" %(db_path,account)
    print(account_file)
    if os.path.isfile(account_file):
    with open(account_file,'r') as f:
    account_data = json.load(f)
    if account_data['password'] == password:
    exp_time_stamp = time.mktime(time.strptime(account_data['expire_date'], "%Y-%m-%d"))
    if time.time() >exp_time_stamp:
    print("33[31;1mAccount [%s] has expired,please contact the back to get a new card!33[0m" % account)
    else: #passed the authentication
    return account_data
    else:
    print("33[31;1mAccount ID or password is incorrect!33[0m")
    else:
    print("33[31;1mAccount [%s] does not exist!33[0m" % account)


    def acc_auth2(account,password):
    '''
    优化版认证接口
    :param account: credit account number
    :param password: credit card password
    :return: if passed the authentication , retun the account object, otherwise ,return None

    '''
    db_api = db_handler.db_handler() #连接数据库 file_execute内存地址
    data = db_api("select * from accounts where account=%s" % account) #执行sql
    if data['password'] == password:
    exp_time_stamp = time.mktime(time.strptime(data['expire_date'], "%Y-%m-%d"))
    if time.time() > exp_time_stamp:
    print("33[31;1mAccount [%s] has expired,please contact the back to get a new card!33[0m" % account)
    else: # passed the authentication
    return data
    else:
    print("33[31;1mAccount ID or password is incorrect!33[0m")

    def acc_login(user_data,log_obj):
    '''
    account login func
    :user_data: user info data , only saves in memory
    :return:
    '''
    retry_count = 0
    while user_data['is_authenticated'] is not True and retry_count < 3 :
    account = input("33[32;1maccount:33[0m").strip()
    password = input("33[32;1mpassword:33[0m").strip()
    auth = acc_auth2(account, password)
    if auth: #not None means passed the authentication
    user_data['is_authenticated'] = True
    user_data['account_id'] = account
    #print("welcome")
    return auth
    retry_count +=1
    else:
    log_obj.error("account [%s] too many login attempts" % account)
    exit()


    复制代码
     1 #!/usr/bin/env python
     2 # -*- coding: utf-8 -*-
     3 import os
     4 from core import db_handler
     5 from conf import settings
     6 from core import logger
     7 import json
     8 import time
     9 
    10 
    11 
    12 def login_required(func):
    13     "验证用户是否登录"
    14 
    15     def wrapper(*args,**kwargs):
    16         #print('--wrapper--->',args,kwargs)
    17         if args[0].get('is_authenticated'):
    18             return func(*args,**kwargs)
    19         else:
    20             exit("User is not authenticated.")
    21     return wrapper
    22 
    23 
    24 def acc_auth(account,password):
    25     '''
    26     account auth func
    27     :param account: credit account number
    28     :param password: credit card password
    29     :return: if passed the authentication , retun the account object, otherwise ,return None
    30     '''
    31     db_path = db_handler.db_handler(settings.DATABASE)
    32     account_file = "%s/%s.json" %(db_path,account)
    33     print(account_file)
    34     if os.path.isfile(account_file):
    35         with open(account_file,'r') as f:
    36             account_data = json.load(f)
    37             if account_data['password'] == password:
    38                 exp_time_stamp = time.mktime(time.strptime(account_data['expire_date'], "%Y-%m-%d"))
    39                 if time.time() >exp_time_stamp:
    40                     print("33[31;1mAccount [%s] has expired,please contact the back to get a new card!33[0m" % account)
    41                 else: #passed the authentication
    42                     return  account_data
    43             else:
    44                 print("33[31;1mAccount ID or password is incorrect!33[0m")
    45     else:
    46         print("33[31;1mAccount [%s] does not exist!33[0m" % account)
    47 
    48 
    49 def acc_auth2(account,password):
    50     '''
    51     优化版认证接口
    52     :param account: credit account number
    53     :param password: credit card password
    54     :return: if passed the authentication , retun the account object, otherwise ,return None
    55 
    56     '''
    57     db_api = db_handler.db_handler()  #连接数据库 file_execute内存地址
    58     data = db_api("select * from accounts where account=%s" % account) #执行sql
    59     if data['password'] == password:
    60         exp_time_stamp = time.mktime(time.strptime(data['expire_date'], "%Y-%m-%d"))
    61         if time.time() > exp_time_stamp:
    62             print("33[31;1mAccount [%s] has expired,please contact the back to get a new card!33[0m" % account)
    63         else:  # passed the authentication
    64             return data
    65     else:
    66         print("33[31;1mAccount ID or password is incorrect!33[0m")
    67 
    68 def acc_login(user_data,log_obj):
    69     '''
    70     account login func
    71     :user_data: user info data , only saves in memory
    72     :return:
    73     '''
    74     retry_count = 0
    75     while user_data['is_authenticated'] is not True and retry_count < 3 :
    76         account = input("33[32;1maccount:33[0m").strip()
    77         password = input("33[32;1mpassword:33[0m").strip()
    78         auth = acc_auth2(account, password)
    79         if auth: #not None means passed the authentication
    80             user_data['is_authenticated'] = True
    81             user_data['account_id'] = account
    82             #print("welcome")
    83             return auth
    84         retry_count +=1
    85     else:
    86         log_obj.error("account [%s] too many login attempts" % account)
    87         exit()
    复制代码

    core/db_handler.py

    #!_*_coding:utf-8_*_
    #__author__:"Alex Li"

    '''
    handle all the database interactions
    '''
    import json,time ,os
    from conf import settings
    def file_db_handle(conn_params):
    '''
    parse the db file path
    :param conn_params: the db connection params set in settings
    :return:
    '''
    # print('file db:',conn_params)
    #db_path ='%s/%s' %(conn_params['path'],conn_params['name'])
    return file_execute
    def db_handler():
    '''
    connect to db
    :param conn_parms: the db connection params set in settings
    :return:a
    '''
    conn_params = settings.DATABASE
    if conn_params['engine'] == 'file_storage':
    return file_db_handle(conn_params)
    elif conn_params['engine'] == 'mysql':
    pass #todo

    def file_execute(sql,**kwargs):
    conn_params = settings.DATABASE
    db_path = '%s/%s' % (conn_params['path'], conn_params['name'])

    # print(sql,db_path)
    sql_list = sql.split("where")
    # print(sql_list)
    if sql_list[0].startswith("select") and len(sql_list)> 1:#has where clause
    column,val = sql_list[1].strip().split("=")

    if column == 'account':
    account_file = "%s/%s.json" % (db_path, val)
    print(account_file)
    if os.path.isfile(account_file):
    with open(account_file, 'r') as f:
    account_data = json.load(f)
    return account_data
    else:
    exit("33[31;1mAccount [%s] does not exist!33[0m" % val )

    elif sql_list[0].startswith("update") and len(sql_list)> 1:#has where clause
    column, val = sql_list[1].strip().split("=")
    if column == 'account':
    account_file = "%s/%s.json" % (db_path, val)
    #print(account_file)
    if os.path.isfile(account_file):
    account_data = kwargs.get("account_data")
    with open(account_file, 'w') as f:
    acc_data = json.dump(account_data, f)
    return True


    复制代码
     1 #!_*_coding:utf-8_*_
     2 #__author__:"Alex Li"
     3 
     4 '''
     5 handle all the database interactions
     6 '''
     7 import json,time ,os
     8 from  conf import settings
     9 def file_db_handle(conn_params):
    10     '''
    11     parse the db file path
    12     :param conn_params: the db connection params set in settings
    13     :return:
    14     '''
    15     # print('file db:',conn_params)
    16     #db_path ='%s/%s' %(conn_params['path'],conn_params['name'])
    17     return file_execute
    18 def db_handler():
    19     '''
    20     connect to db
    21     :param conn_parms: the db connection params set in settings
    22     :return:a
    23     '''
    24     conn_params = settings.DATABASE
    25     if conn_params['engine'] == 'file_storage':
    26         return file_db_handle(conn_params)
    27     elif conn_params['engine'] == 'mysql':
    28         pass #todo
    29 
    30 
    31 
    32 def file_execute(sql,**kwargs):
    33     conn_params = settings.DATABASE
    34     db_path = '%s/%s' % (conn_params['path'], conn_params['name'])
    35 
    36     # print(sql,db_path)
    37     sql_list = sql.split("where")
    38     # print(sql_list)
    39     if sql_list[0].startswith("select") and len(sql_list)> 1:#has where clause
    40         column,val = sql_list[1].strip().split("=")
    41 
    42         if column == 'account':
    43             account_file = "%s/%s.json" % (db_path, val)
    44             print(account_file)
    45             if os.path.isfile(account_file):
    46                 with open(account_file, 'r') as f:
    47                     account_data = json.load(f)
    48                     return account_data
    49             else:
    50                 exit("33[31;1mAccount [%s] does not exist!33[0m" % val )
    51 
    52     elif sql_list[0].startswith("update") and len(sql_list)> 1:#has where clause
    53         column, val = sql_list[1].strip().split("=")
    54         if column == 'account':
    55             account_file = "%s/%s.json" % (db_path, val)
    56             #print(account_file)
    57             if os.path.isfile(account_file):
    58                 account_data = kwargs.get("account_data")
    59                 with open(account_file, 'w') as f:
    60                     acc_data = json.dump(account_data, f)
    61                 return True
    复制代码

    core/logger.py

    #!/usr/bin/env python
    # -*- coding: utf-8 -*-

    '''
    handle all the logging works
    '''

    import logging
    from conf import settings

    def logger(log_type):

    #create logger
    logger = logging.getLogger(log_type)
    logger.setLevel(settings.LOG_LEVEL)


    # create console handler and set level to debug
    ch = logging.StreamHandler()
    ch.setLevel(settings.LOG_LEVEL)

    # create file handler and set level to warning
    log_file = "%s/log/%s" %(settings.BASE_DIR, settings.LOG_TYPES[log_type])
    fh = logging.FileHandler(log_file)
    fh.setLevel(settings.LOG_LEVEL)
    # create formatter
    formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')

    # add formatter to ch and fh
    ch.setFormatter(formatter)
    fh.setFormatter(formatter)

    # add ch and fh to logger
    logger.addHandler(ch)
    logger.addHandler(fh)

    return logger
    # 'application' code
    '''logger.debug('debug message')
    logger.info('info message')
    logger.warn('warn message')
    logger.error('error message')
    logger.critical('critical message')'''


    复制代码
     1 #!/usr/bin/env python
     2 # -*- coding: utf-8 -*-
     3 
     4 '''
     5 handle all the logging works
     6 '''
     7 
     8 import logging
     9 from conf import settings
    10 
    11 def logger(log_type):
    12 
    13     #create logger
    14     logger = logging.getLogger(log_type)
    15     logger.setLevel(settings.LOG_LEVEL)
    16 
    17 
    18     # create console handler and set level to debug
    19     ch = logging.StreamHandler()
    20     ch.setLevel(settings.LOG_LEVEL)
    21 
    22     # create file handler and set level to warning
    23     log_file = "%s/log/%s" %(settings.BASE_DIR, settings.LOG_TYPES[log_type])
    24     fh = logging.FileHandler(log_file)
    25     fh.setLevel(settings.LOG_LEVEL)
    26     # create formatter
    27     formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')
    28 
    29     # add formatter to ch and fh
    30     ch.setFormatter(formatter)
    31     fh.setFormatter(formatter)
    32 
    33     # add ch and fh to logger
    34     logger.addHandler(ch)
    35     logger.addHandler(fh)
    36 
    37     return logger
    38     # 'application' code
    39     '''logger.debug('debug message')
    40     logger.info('info message')
    41     logger.warn('warn message')
    42     logger.error('error message')
    43     logger.critical('critical message')'''
    复制代码

    db/account_sample.py

    #!/usr/bin/env python
    # -*- coding: utf-8 -*-


    import json
    acc_dic = {
    'id': 1234,
    'password': 'abc',
    'credit': 15000,
    'balance': 15000,
    'enroll_date': '2016-01-02',
    'expire_date': '2021-01-01',
    'pay_day': 22,
    'status': 0 # 0 = normal, 1 = locked, 2 = disabled
    }

    print(json.dumps(acc_dic))


    复制代码
     1 #!/usr/bin/env python
     2 # -*- coding: utf-8 -*-
     3 
     4 
     5 import json
     6 acc_dic = {
     7     'id': 1234,
     8     'password': 'abc',
     9     'credit': 15000,
    10     'balance': 15000,
    11     'enroll_date': '2016-01-02',
    12     'expire_date': '2021-01-01',
    13     'pay_day': 22,
    14     'status': 0 # 0 = normal, 1 = locked, 2 = disabled
    15 }
    16 
    17 print(json.dumps(acc_dic))
    复制代码
  • 相关阅读:
    HTML
    Linux 入门记录:十一、Linux 用户基础
    Linux 入门记录:十、Linux 下获取帮助
    Linux 入门记录:九、Linux 文件系统挂载管理
    Linux 入门记录:八、Linux 文件系统
    Linux 入门记录:七、fdisk 分区工具
    Linux 入门记录:六、Linux 硬件相关概念(硬盘、磁盘、磁道、柱面、磁头、扇区、分区、MBR、GPT)
    Linux 入门记录:五、vi、vim 编辑器
    Linux 入门记录:四、Linux 系统常用命令
    Linux 入门记录:三、Linux 文件基本操作管理
  • 原文地址:https://www.cnblogs.com/larry-luo/p/10857043.html
Copyright © 2011-2022 走看看