Django中如何将POST请求提交的数据转换为JSON格式
问题分析
det初始化类型错误:你声明了det = []是列表,却直接用det[字符串键] = 值的方式赋值,列表仅支持数字索引,必然触发异常被捕获跳过,导致det始终为空- prod结构组装逻辑错误:同一prod条目下的多个字段会被拆分为多个独立的单键字典,没有合并到同一个字典对象中,且自行维护的count变量逻辑完全不符合索引匹配规则
- 正则表达式冗余:模式中
\w+后的.属于多余字符,会额外匹配任意1个字符,可能导致匹配异常;且循环中重复调用match方法没有复用结果,性能低下
修复后代码
if post: import re # 修正正则,去掉多余的点 pattDet = re.compile(r'^([a-zA-Z_]\w+)\[([0-9_\-][\w\-]*)\]\[([a-zA-Z_\-][\w\-]*)\]$') pattProd = re.compile(r'^([a-zA-Z_]\w+)\[([0-9_\-][\w\-]*)\]\[([0-9_\-][\w\-]*)\]\[([a-zA-Z_\-][\w\-]*)\]$') # 初始化结构:det是列表,每个元素是对应索引的det字典 det_list = [] # prod是列表,每个det索引对应一个prod列表,prod列表里是每个商品的字典 prod_list = [] for post_name, value in post.items(): # 先处理det类型字段 det_match = pattDet.match(post_name) if det_match and det_match.group(1) == 'det': det_idx = int(det_match.group(2)) det_key = det_match.group(3) # 索引不够的话先补空字典 while len(det_list) <= det_idx: det_list.append({}) det_list[det_idx][det_key] = value continue # 再处理prod类型字段 prod_match = pattProd.match(post_name) if prod_match and prod_match.group(1) == 'prod': det_idx = int(prod_match.group(2)) prod_idx = int(prod_match.group(3)) prod_key = prod_match.group(4) # 先补det层级的空prod列表 while len(prod_list) <= det_idx: prod_list.append([]) # 再补prod层级的空字典 while len(prod_list[det_idx]) <= prod_idx: prod_list[det_idx].append({}) prod_list[det_idx][prod_idx][prod_key] = value # 组装结果,这里如果det只有1个可以直接取det_list[0],按需调整 result = { 'det': det_list, 'prod': prod_list }
运行后输出示例
{ "det": [ { "CNPJ": "8768678678678", "UF": "SP", "dhEmi": "2021-07-13T08:26:30-03:00", "nNF": "8267", "xNome": "INDÚSTRIA" } ], "prod": [ [ { "CFOP": "6102", "NCM": "84384000", "UF": "SP", "aliquotaInterna": "18", "counter": "1", "mva": "34", "tributacaoEstadual": "7", "vICMSST": "0", "vICMS": "25.74", "vIPI": "0", "vProd": "367.68", "xProd": "FUSO" }, { "CFOP": "6102", "NCM": "84384000", "UF": "SP", "aliquotaInterna": "18", "counter": "2", "mva": "23", "tributacaoEstadual": "7", "vICMSST": "0", "vICMS": "15.96", "vIPI": "0", "vProd": "228.07", "xProd": "PORCA" } ] ] }
如果你的业务场景下det只有1条数据,也可以直接取det_list[0]将det设置为字典类型而非列表,按需调整即可。
内容的提问来源于stack exchange,提问作者marcelo.delta
相关产品推荐
相关产品推荐

