Skip to content
Toggle navigation
Toggle navigation
This project
Loading...
Sign in
周伟奇
/
bmw-ocr
Go to a project
Toggle navigation
Toggle navigation pinning
Projects
Groups
Snippets
Help
Project
Activity
Repository
Graphs
Network
Create a new issue
Commits
Issue Boards
Files
Commits
Network
Compare
Branches
Tags
24977d55
authored
2024-07-24 10:16:49 +0800
by
冯轩
Browse Files
Options
Browse Files
Tag
Download
Email Patches
Plain Diff
ADD:财报逻辑
1 parent
5c3c9d17
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
218 additions
and
10 deletions
src/apps/doc/consts.py
src/celery_compare/tasks.py
src/common/tools/comparison.py
src/common/tools/mssql_script28.py
src/apps/doc/consts.py
View file @
24977d5
...
...
@@ -1247,6 +1247,7 @@ FSM_CONTRACT_WEP_FIELD = 'fsm_wep_ocr'
FSM_CONTRACT_MSI_FIELD
=
'fsm_msi_ocr'
FSM_CONTRACT_SC_FIELD
=
'fsm_sc_ocr'
FSM_CONTRACT_SC2_FIELD
=
'fsm_sc2_ocr'
FS_FIELD
=
'fs_ocr'
BS_CLASSIFY
=
10089
...
...
@@ -1504,6 +1505,7 @@ SE_BD_FIELD = ['被保险人姓名', '被保险人证件号码', '车架号', '
JDMPV_VALUE
=
[
'-'
,
'--'
,
'0
%
'
,
'0.00'
,
'/'
,
'0'
,
''
]
JYPZ_TYPE_1
=
[
'二手车交易凭证'
]
JYPZ_TYPE_2
=
[
'BMW官方认证二手车交易凭证'
,
'二手车交易凭证'
]
SE_FS_FIELD
=
[
'Hash值'
,
'公章'
,
'财年'
,
'资产负债表内容'
,
'利润表内容'
]
SE_BANK_FIELD
=
[
'accountNo'
,
'bankName'
]
SE_DDA_FIELD
=
[
'applicationId(1)'
,
'applicationId(2)'
,
'bankName'
,
'companyName'
,
'customerName'
,
'idNum'
,
'accountHolderName'
,
'accountNo'
]
...
...
@@ -1817,8 +1819,11 @@ BS_EN = 'Bank Statement'
HIL_CONTRACT_1_EN
=
'售后回租合同'
HIL_CONTRACT_2_EN
=
'车辆租赁抵押合同'
HIL_CONTRACT_3_EN
=
'车辆处置协议'
FS_EN
=
'Financial Statement'
FSS_EN
=
'Financial Statement Supplementary'
DDA_NO_FIND
=
'需人工查看DDA或截图'
FS_NO_FIND
=
'未提供财报或财报不完整'
SKIP_CARD
=
{
SME_BL_EN
}
...
...
@@ -2105,16 +2110,6 @@ HT_QRS_COMPARE_LOGIC = {
'合同编号'
:
(
'合同编号'
,
'se_qrs_compare'
,
{},
'请确认是否提供合格的送达地址确认书'
),
}
FINANCIAL_STATEMENT_COMPARE_LOGIC
=
{
'Hash值'
:
(
'Hash值'
,
''
,
{},
'财报Hash值与系统不一致'
),
'公章'
:
(
'公章'
,
''
,
{},
'财报无公章'
),
}
FINANCIAL_STATEMENT_SUPPLEMENTARY_COMPARE_LOGIC
=
{
'公司名称'
:
(
'公司名称'
,
''
,
{},
'财报情况说明公司名称错误'
),
'公章'
:
(
'公章'
,
''
,
{},
'财报情况说明无公章'
),
}
HT_COMPARE_LOGIC
=
{
'合同编号-每页'
:
(
'合同编号-每页'
,
'se_list_compare'
,
{},
'合同编号与系统不一致'
),
# '合同编号-每页(no-asp)': ('合同编号-每页', 'se_list_compare', {'pop_last': True}, '合同编号与系统不一致'),
...
...
@@ -2169,6 +2164,15 @@ HT_COMPARE_LOGIC = {
'无ASP产品'
:
(
'无ASP产品'
,
'se_self_compare_other_asp'
,
{},
GZS_REASON_1
),
}
# 格式:'excel字段名':('数据库字段名','比对逻辑','特殊处理可以忽略','比对不合格时的返回内容')
FS_COMPARE_LOGIC
=
{
'Hash值'
:
(
'code'
,
'hash_code_compare'
,
{},
'财报Hash值与系统不一致'
),
'公章'
:
(
'stamp'
,
'stamp_dict_compare'
,
{},
'财报无公章'
),
'财年'
:
(
'财年'
,
'fiscal_year_compare'
,
{},
'财报所属财年错误'
),
'资产负债表内容'
:
(
'资产负债表内容'
,
'ocr_list_not_zero_compare'
,
{},
'财报资产负债表为空'
),
'利润表内容'
:
(
'利润表内容'
,
'ocr_list_not_zero_compare'
,
{},
'财报利润表为空'
),
}
AFC_HT_DATE_FIELDS
=
[
'主借人日期'
,
'共借人日期'
,
'保证人日期1'
,
'保证人日期2'
]
# MVC_OCR_FIELD = 'mvc_ocr'
...
...
@@ -2197,6 +2201,7 @@ SE_COMPARE_FIELD = {
HIL_CONTRACT_1_EN
:
(
HIL_CONTRACT_1_FIELD
,
HIL_CONTRACT_1_COMPARE_LOGIC
,
False
),
HIL_CONTRACT_2_EN
:
(
HIL_CONTRACT_2_FIELD
,
HIL_CONTRACT_2_COMPARE_LOGIC
,
False
),
HIL_CONTRACT_3_EN
:
(
HIL_CONTRACT_3_FIELD
,
HIL_CONTRACT_3_COMPARE_LOGIC
,
False
),
FS_EN
:
(
FS_FIELD
,
FS_COMPARE_LOGIC
,
False
),
}
SE_COMPARE_FIELD_AUTO
=
{
...
...
src/celery_compare/tasks.py
View file @
24977d5
...
...
@@ -953,6 +953,12 @@ def get_se_cms_compare_info_auto(application_id, last_obj, application_entity, d
if
individual_info
[
'applicantType'
]
==
consts
.
APPLICANT_TYPE_ORDER
[
0
]
and
not
is_corporate
:
is_cdfl_bo
=
True
# CHINARPA-4660 是否公户判断
is_bo_tccor
=
False
customersubType
=
individual_info
.
get
(
'customersubType'
,
''
)
if
individual_info
[
'applicantType'
]
==
consts
.
APPLICANT_TYPE_ORDER
[
0
]
and
customersubType
==
'TCCOR'
:
is_bo_tccor
=
True
for
id_info
in
individual_info
.
get
(
'IDInformation'
,
[]):
if
id_info
.
get
(
'idType'
)
in
consts
.
SE_CMS_FIRST_ID_FIELD_MAPPING
:
license_en
,
is_prc
=
consts
.
SE_CMS_FIRST_ID_FIELD_MAPPING
[
id_info
[
'idType'
]]
...
...
@@ -1120,6 +1126,24 @@ def get_se_cms_compare_info_auto(application_id, last_obj, application_entity, d
# vehicle_info[consts.UCI_EN] = vehicle_field_input
compare_info
[
'vehicleInfo'
]
=
vehicle_info
# 公户财务报表-------------------------------------------------------------------------------------------------
financial_statement_info
=
{}
financial_statement_input
=
[]
hashCode
=
cms_info
.
get
(
'hashCode'
,
''
)
fiscalYear
=
cms_info
.
get
(
'fiscalYear'
,
''
)
totalAssets
=
cms_info
.
get
(
'totalAssets'
,
0
)
totalLiabilitiesAndOwnersEquity
=
cms_info
.
get
(
'totalLiabilitiesAndOwnersEquity'
,
0
)
netProfit
=
cms_info
.
get
(
'netProfit'
,
0
)
if
is_bo_tccor
:
financial_statement_input
.
append
((
consts
.
SE_FS_FIELD
[
0
],
hashCode
))
financial_statement_input
.
append
((
consts
.
SE_FS_FIELD
[
1
],
consts
.
SE_STAMP_VALUE
))
financial_statement_input
.
append
((
consts
.
SE_FS_FIELD
[
2
],
fiscalYear
))
financial_statement_input
.
append
((
consts
.
SE_FS_FIELD
[
3
],
[
totalAssets
,
totalLiabilitiesAndOwnersEquity
]))
financial_statement_input
.
append
((
consts
.
SE_FS_FIELD
[
4
],
netProfit
))
financial_statement_info
[
consts
.
FS_EN
]
=
financial_statement_input
compare_info
[
'financialStatementInfo'
]
=
financial_statement_info
# 银行卡-------------------------------------------------------------------------------------------------------
bank_info
=
{}
bank_name
=
cms_info
.
get
(
'bankAccountDetails'
,
{})
.
get
(
'bankName'
,
''
)
...
...
@@ -2523,6 +2547,107 @@ def se_compare_license(license_en, ocr_res_dict, field_list):
return
result_field_list
,
no_ocr_result
,
field_img_path_dict
def
se_fs_compare
(
license_en
,
ocr_res_dict
,
field_list
):
ocr_field
,
compare_logic
,
special_expiry_date
=
consts
.
SE_COMPARE_FIELD
[
license_en
]
is_find
=
False
no_ocr_result
=
False
special_expiry_date_slice
=
False
result_field_list
=
[]
section_img_info
=
dict
()
field_img_path_dict
=
dict
()
ocr_res_str
=
ocr_res_dict
.
get
(
ocr_field
)
if
ocr_res_str
is
not
None
:
ocr_res_list
=
json
.
loads
(
ocr_res_str
)
length
=
len
(
ocr_res_list
)
# 先判断最后一次上传的文件是不是包括3个,如果不是直接返回"未提供财报或财报不完整"
last_ocr_str
=
ocr_res_list
[
length
-
1
]
if
len
(
last_ocr_str
.
get
(
'code'
,{}))
!=
3
or
len
(
last_ocr_str
.
get
(
'stamp'
,{}))
!=
3
:
compare_log
.
info
(
'{0} [se_fs_compare] last ocr result len < 3'
.
format
(
log_base
))
else
:
for
res_idx
in
range
(
length
-
1
,
-
1
,
-
1
):
if
is_find
:
break
for
idx
,
(
name
,
value
)
in
enumerate
(
field_list
):
ocr_str
=
ocr_res_list
[
res_idx
]
.
get
(
compare_logic
[
name
][
0
])
#hash值/公章 不需要ocr结果,所以即使为空也可以进入比对
if
isinstance
(
ocr_str
,
str
)
or
ocr_str
==
'code'
or
ocr_str
==
'stamp'
:
result
=
getattr
(
cp
,
compare_logic
[
name
][
1
])(
value
,
ocr_str
,
**
compare_logic
[
name
][
2
])
no_key
=
False
else
:
result
=
consts
.
RESULT_N
ocr_str
=
empty_str
no_key
=
True
if
idx
==
0
and
result
==
consts
.
RESULT_N
and
length
>
1
:
break
is_find
=
True
section_img_info
[
consts
.
SECTION_IMG_PATH_KEY
]
=
ocr_res_list
[
res_idx
]
.
get
(
consts
.
SECTION_IMG_PATH_KEY
,
''
)
section_img_info
[
consts
.
ALL_POSITION_KEY
]
=
ocr_res_list
[
res_idx
]
.
get
(
consts
.
ALL_POSITION_KEY
,
{})
if
special_expiry_date
:
section_img_info
[
consts
.
SECTION_IMG_PATH_KEY_2
]
=
ocr_res_list
[
res_idx
]
.
get
(
consts
.
SECTION_IMG_PATH_KEY_2
,
''
)
section_img_info
[
consts
.
ALL_POSITION_KEY_2
]
=
ocr_res_list
[
res_idx
]
.
get
(
consts
.
ALL_POSITION_KEY_2
,
{})
img_path
=
ocr_res_list
[
res_idx
]
.
get
(
consts
.
IMG_PATH_KEY
,
''
)
if
result
==
consts
.
RESULT_N
else
empty_str
if
isinstance
(
value
,
list
):
value
=
json
.
dumps
(
value
,
ensure_ascii
=
False
)
error_type
=
empty_error_type
if
result
==
consts
.
RESULT_Y
else
ErrorType
.
OCR
.
value
result_field_list
.
append
((
name
,
value
,
result
,
ocr_str
,
img_path
,
error_type
,
compare_logic
[
name
][
3
]))
else
:
no_ocr_result
=
True
if
not
is_find
:
for
name
,
value
in
field_list
:
if
isinstance
(
value
,
list
):
value
=
json
.
dumps
(
value
,
ensure_ascii
=
False
)
no_find_str
=
consts
.
FS_NO_FIND
result_field_list
.
append
((
name
,
value
,
consts
.
RESULT_N
,
empty_str
,
empty_str
,
ErrorType
.
NF
.
value
,
no_find_str
))
if
is_find
:
section_img_path
=
section_img_info
.
get
(
consts
.
SECTION_IMG_PATH_KEY
,
''
)
if
os
.
path
.
exists
(
section_img_path
):
failed_field
=
[]
base_img_path
=
empty_str
for
name
,
_
,
result
,
_
,
img_path
,
_
,
_
in
result_field_list
:
if
result
==
consts
.
RESULT_N
:
if
special_expiry_date_slice
and
name
==
'idExpiryDate'
:
continue
failed_field
.
append
(
name
)
if
base_img_path
==
empty_str
:
base_img_path
=
img_path
if
len
(
failed_field
)
>
0
:
info
=
section_img_info
.
get
(
consts
.
ALL_POSITION_KEY
,
{})
section_position
=
info
.
get
(
consts
.
POSITION_KEY
,
{})
section_angle
=
info
.
get
(
consts
.
ANGLE_KEY
,
0
)
try
:
last_img
=
img_process
(
section_img_path
,
section_position
,
section_angle
)
except
Exception
as
e
:
for
field
in
failed_field
:
field_img_path_dict
[
field
]
=
base_img_path
else
:
pre
,
suf
=
os
.
path
.
splitext
(
section_img_path
)
for
field
in
failed_field
:
try
:
res_field
=
compare_logic
[
field
][
0
]
is_valid
,
coord_tuple
=
field_build_coordinates
(
info
.
get
(
res_field
,
{}))
if
is_valid
:
save_path
=
'{0}_{1}{2}'
.
format
(
pre
,
field
,
suf
)
field_img
=
last_img
[
coord_tuple
[
0
]:
coord_tuple
[
1
],
coord_tuple
[
2
]:
coord_tuple
[
3
],
:]
cv2
.
imwrite
(
save_path
,
field_img
)
field_img_path_dict
[
field
]
=
save_path
else
:
field_img_path_dict
[
field
]
=
base_img_path
except
Exception
as
e
:
field_img_path_dict
[
field
]
=
base_img_path
return
result_field_list
,
field_img_path_dict
def
se_compare_license_id
(
license_en
,
id_res_list
,
field_list
,
is_auto
):
if
is_auto
:
...
...
@@ -3023,6 +3148,7 @@ def se_compare_process(compare_info, ocr_res_dict, is_gsyh, is_auto, id_res_list
rpa_failure_reason
=
{}
field_result_dict
=
{}
# compare_info 格式: {'financialStatementInfo': {'Financial Statement': [('11', '22'), ('111', '222'), ('1111', '2222')]}}
for
info_key
,
info_value
in
compare_info
.
items
():
if
info_key
in
[
'individualCusInfo'
,
'applicantInformation'
]:
for
idx
,
license_list
in
info_value
.
items
():
...
...
@@ -3104,6 +3230,8 @@ def se_compare_process(compare_info, ocr_res_dict, is_gsyh, is_auto, id_res_list
result_field_list
,
field_img_path_dict
=
se_contract_qrs_compare
(
license_en
,
ocr_res_dict
,
strip_list
)
elif
license_en
==
consts
.
BS_EN
:
result_field_list
,
field_img_path_dict
=
se_bs_compare
(
license_en
,
ocr_res_dict
,
strip_list
,
is_auto
,
aa_type
)
elif
license_en
==
consts
.
FS_EN
:
result_field_list
,
field_img_path_dict
=
se_fs_compare
(
license_en
,
ocr_res_dict
,
strip_list
,
is_auto
,
aa_type
)
else
:
result_field_list
,
_
,
field_img_path_dict
=
se_compare_license
(
license_en
,
ocr_res_dict
,
strip_list
)
...
...
src/common/tools/comparison.py
View file @
24977d5
...
...
@@ -676,6 +676,50 @@ class Comparison:
except
Exception
as
e
:
return
self
.
RESULT_N
def
hash_code_compare
(
self
,
input_str
,
ocr_dict
,
**
kwargs
):
try
:
balance_sheet_hash
=
ocr_dict
.
get
(
'balance_sheet'
,
''
)
income_statement_hash
=
ocr_dict
.
get
(
'income_statement'
,
''
)
cash_flow_statement_hash
=
ocr_dict
.
get
(
'cash_flow_statement'
,
''
)
if
balance_sheet_hash
!=
input_str
or
income_statement_hash
!=
input_str
or
cash_flow_statement_hash
!=
input_str
:
return
self
.
RESULT_N
else
:
return
self
.
RESULT_Y
except
Exception
as
e
:
return
self
.
RESULT_N
def
stamp_dict_compare
(
self
,
input_str
,
ocr_dict
,
**
kwargs
):
try
:
balance_sheet_stamp
=
ocr_dict
.
get
(
'balance_sheet'
,
''
)
income_statement_stamp
=
ocr_dict
.
get
(
'income_statement'
,
''
)
cash_flow_statement_stamp
=
ocr_dict
.
get
(
'cash_flow_statement'
,
''
)
if
balance_sheet_stamp
!=
1
or
income_statement_stamp
!=
1
or
cash_flow_statement_stamp
!=
1
:
return
self
.
RESULT_N
else
:
return
self
.
RESULT_Y
except
Exception
as
e
:
return
self
.
RESULT_N
def
fiscal_year_compare
(
self
,
input_str
,
ocr_list
,
**
kwargs
):
try
:
this_year_str
=
datetime
.
now
()
.
strftime
(
'
%
Y'
)
this_year
=
int
(
this_year_str
)
last_year
=
this_year
-
1
if
input_str
!=
this_year
and
input_str
!=
last_year
:
return
self
.
RESULT_N
return
self
.
RESULT_Y
except
Exception
as
e
:
return
self
.
RESULT_N
def
input_list_not_zero_compare
(
self
,
input_list
,
ocr_list
,
**
kwargs
):
try
:
for
item
in
input_list
:
if
item
==
0
:
return
self
.
RESULT_N
return
self
.
RESULT_Y
except
Exception
as
e
:
return
self
.
RESULT_N
cp
=
Comparison
()
...
...
src/common/tools/mssql_script28.py
0 → 100644
View file @
24977d5
import
pyodbc
hil_sql
=
"""
ALTER TABLE hil_ocr_result ADD fs_ocr nvarchar(max);
ALTER TABLE hil_se_ocr_result ADD fs_ocr nvarchar(max);
ALTER TABLE hil_ocr_result ADD fss_ocr nvarchar(max);
ALTER TABLE hil_se_ocr_result ADD fss_ocr nvarchar(max);
"""
afc_sql
=
"""
ALTER TABLE afc_ocr_result ADD fs_ocr nvarchar(max);
ALTER TABLE afc_se_ocr_result ADD fs_ocr nvarchar(max);
ALTER TABLE afc_ocr_result ADD fss_ocr nvarchar(max);
ALTER TABLE afc_se_ocr_result ADD fss_ocr nvarchar(max);
"""
hil_cnxn
=
pyodbc
.
connect
(
'DRIVER={ODBC Driver 17 for SQL Server};'
,
autocommit
=
True
)
hil_cursor
=
hil_cnxn
.
cursor
()
hil_cursor
.
execute
(
hil_sql
)
hil_cursor
.
close
()
hil_cnxn
.
close
()
afc_cnxn
=
pyodbc
.
connect
(
'DRIVER={ODBC Driver 17 for SQL Server};'
,
autocommit
=
True
)
afc_cursor
=
afc_cnxn
.
cursor
()
afc_cursor
.
execute
(
afc_sql
)
afc_cursor
.
close
()
afc_cnxn
.
close
()
Write
Preview
Styling with
Markdown
is supported
Attach a file
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to post a comment