4.3
复习目录搭建
conf 配置
--settings.py
lib
--common.py 公共方法
core
--src.py
db
--user_data
--user.json
--db_handlder.py
interface 核心业务逻辑代码
--user_interface
--bank_interface
--shop_interface
log
--.log
start.py
readme.md
写程序
start.py
sys.path.append(os.path.dirname(__file__))
from core import src
if __name__ == '__main__':
src.run()
编写顺序
注册
1. start.py,添加环境变量
2. src.py ----> run()
1. while循环打印菜单
2. 接收输入编号
3. 创建src中一系列函数及函数字典
1. 在src中,调用用户选择的函数
4. 注册功能
1. while循环,接收输入用户名和两次密码
2. 判断两次密码是否一致
3. 调用逻辑接口层的`register_interface`
1. 调用 `db_handler` 中的`getUserIfo`,查看是否有数据返回
1. 写数据处理层中的getUserIfo
1. 根据传来的用户名拼接json文件
2. 判断json文件是否存在 `os.path.exist`
1. 存在则返回文件内容
2. 不存在则返回空
2. 接收dbhandler的数据,判断
1. 存在,返回False,跳转步骤4
1. 视图层提示用户已经注册,重新输入
3. 不存在,返回True
4. 创建user_dic
5. 密码md5加密
1. lib --->common.py 写加密方法
2. 调用db_handler中的save方法
1. 从user_dic 得到用户名,拼接用户名.json路径
2. 从settings中得到`db/user_data`的路径
3. 拼接user.json 和user_data
4. with open(user_path),json.dump(user_dic)
4. flag,msg = register_interface(),返回结果到视图层
1. 用户名存在,continue,重新输入
2. 注册成功,提示信息
登陆功能
登陆接口
1. login函数
2. 接收用户名,密码的输入
3. 调用login_interface
1. db_handler 中的getUserInfo,看用户是否存在
1. 用户不存在,return False,note
2. 用户存在,使用common中的方法加密密码
3. 与user_dic中的密码比较
1. 一致,return True,成功
2. global login_user ,改变全局变量
登陆认证装饰
1. from src import login_user
2. login_user 是否为None
1. 不是None,正常运行被装饰的方法,res = func(*args,*kwargs),return res
2. Login_user为None,调用src.login
3. res = func(*args,*kwargs),return res
3. return wrapper
src.查看余额
调用db_handler getUserInfo(account)
得到user_dic['balance']
src.提现
1. 接收金额
2. 判断是否是数字
1. 不是,重新输入
3. 是数字,调用withdraw_interface(account,amount)
1. getUserInfo---->user_dic[’balance’]
2. 金额*5% 手续费 int
3. 金额+手续费是否小于余额
1. 大于,return False ,余额不足
4. 小于,balance - 提现金额,得到新的user_dic
5. db_handler 中save方法,保存新的user_dic
6. return True,提现成功
4. 视图层接收return,输出msg
还款
@login_auth
src.还款()
1. while循环
2. 接收用户输入金额
3. 判断是否是纯数字
4. 调用bank_interface中的repay_interface
1. getUserInfo(acount)
2. 原来的余额 加 还款的金额
int(user_dic[’balance’]) += int(repay_amount)
3. 更新更改后的数据,调用db_handler中的save(user_dic)
4. 纪录日志
5. return True,还款成功提示消息
5. flag,msg = True,还款成功
6. 打印msg
转账
@login_auth
src.转账
1. 接收用户输入的转账目标用户to_user
2. 接收转账的金额
3. 判断输入的金额是否是纯数字
1. 不是数字,continue 重新输入
4. 是纯数字,调用bank_interface 中的transfer_interface
1. transfer_interface(account,to_user,amount)
接收当前用户login_user,要转账的对象to_user,转账金额amount
2. 获取当前用户的信息,db_handler.getUserInfo(account),user_dic
3. 判断目标用户是否存在
getUserInfo(to_user)
1. 用户不存在,return False,提示用户不存在
4. 用户存在,判断当前用户余额是否足够
1. 余额不足,return False,提示余额不足
5. 余额足够,给当前用户减钱,目标用户加钱
login_user_dic[’balance’] -= amount
to_user_dic[’balance’] += amount
6. 保存当前用户数据,目标用户数据
db_handler.save(login_user_dic)
db_handler.save(to_user_dic)
7. 纪录日志
8. return True,转账成功
5. 视图层打印接收判断
if flag: 成功
else: 失败
查看流水
纪录bank_interface中的所有操作,转账操作需要给当前用户和目标用户都纪录流水
每次使用save_json(user_dic)之前,对用户的user_dic写入流水
user_dic['flow'].append(f'{login_user} 转账 {amount}')
查看流水
@common.login_auth
def check_flow():
flow = bank_interface.chec_flow_interface(login_user)
if flow:
for i in flow:
print(i)
else:
print('当前没有流水')
def chec_flow_interface(login_user):
return db_handler.getUserInfo(login_user)['flow']
管理员功能
在user_dic 里再加一个属性,account_type,如果是user就普通登陆,如果是admin就是管理员用户。把管理员功能放到core下的admin里
冻结账户:改变user_dic中的locked 为True,登陆的时候加一层判断 if user_dic['locked'] ,则提示已被锁定
from core import admin
def admin_run():
admin.run()
# core---->admin.py
from core import src
from interface import admin_interface
def add_user():
src.register()
def change_balance():
# 输入需要修改的用户
while True:
change_user = input('请输入需要修改额度的用户:').strip
change_balance = input('输入要修改的额度:')
if not change_balance.isdigit():
print('请输入数字')
continue
# 调用修改额度接口
flag,msg = admin_interface.change_balance_interface(change_user,change_balance)
if flag:
print(msg)
break
else:
print(msg)
# 修改user_dic中的locked,由false 改为true
def lock_account():
while True:
admin_func = {
'1': add_user,
'2':change_balance,
'3':lock_account,
}
def admin_run():
while True:
print('''
1 添加账户 add user
2 修改额度 change balance
3 冻结账户 lock account
''')
choice = input('输入管理员功能编号:').strip()
if choice not in func_dic:
print('功能编号错误')
continue
admin_func[choice]()
# admin_interface
def change_balance_interface(uer_name,balance):
user_dic = db_handler.getUserInfo(user_name)
if user_dic:
user_dic['balance'] = int(balance)
def lock_user(user_name):
user_dic = db_handler.getUserInfo(user_name)
if user_dic:
user_dic['locked'] = True
...
购物功能
@common.login_auth
shopping
-
创建商品字典
shop_lis = [
['灌汤包',30],
['车仔面',20],
['牛杂',40],
]
-
在视图层初始化购物车字典,商品名作为字典键,[单价,数量] 列表作为字典值
-
打印商品信息,让用户选择,使用枚举
# enumerate (可迭代对象) ----> 可迭代对象的索引,索引对应的值 for item in enumerate(shop_lis): shop_name,shop_price = shop print(f'商品编号[{index}]',f'商品名称[{shop_name}]',f'商品价格[{shop_price}]') choice = input('请输入商品编号:') if not choice.isdigit(): print('商品编号错误') continue # 获取商品名和单价 shop_name,shop_price = shop_list[choice] # 加入购物车 # 判断用户选择的商品是否重复,重复则数量+1 if shop_name in shopping_car: shopping_car[shop_name][1] += 1 else: shopping_cart[shop_name] = [shop_price,1] ...
文字流程
1. 登陆认证装饰器
2. 创建商品列表,[商品名,单价]
3. 初始化购物车,空字典
4. while循环
1. for 循环商品列表,打印商品,用enumerate
2. 接收用户输入的商品编号,输入y可以支付,输入n退出
3. 判断编号是否正确
1. 不正确,continue再循环
4. 输入编号,将商品加入购物车
1. 判断当前商品是否添加过购物车
1. 添加过,则购物车数量 + 1
2. 没添加过,创建key:value对,商品名:单价,数量默认为1
5. 输入y,结算
1. 购物车为空,输出提示信息
2. 购物车不为空,调用shop_interface中的功能
1. 计算消费总金额
for value,num in shopping_car:
coust += value*num
2. 导入银行接口 pay_interface(login_user,cost)
1. getUserInfo
2. 判断用户金额是否足够
1. 余额不足,return False,提示信息
3. 余额够,user_dic[’balance’] -= cost
4. flow 纪录消费流水
5. db_handler.save(user_dic)保存数据
6. return True
3. 判断银行接口返回值
6. 判断结果打印msg
改进:
- 将视图层中的添加购物车功能改为使用shop_interface中的接口
- 每次选择完成后打印当前购物车
清空购物车:getUserInfo后改变user_dic为空,再save
查看购物车
user_dic = db_handler.getUserInfo(ccount)
user_dic[’shop_car’]
日志
日志功能在接口层使用
# common.py
import logging.config
from conf import settings
def get_logger(log_type):
logging.config.dictConfig(settings.LOGGING_DIC)
logger = logging.getLogger(log_type)
return logger
使用的时候,在不同的逻辑处理层,根据不同的类型传入不同的对象给logger
from lib import common
user_logger = common.getLogger()
user_