784 lines
30 KiB
Python
784 lines
30 KiB
Python
# -*- coding: utf-8 -*-
|
|
# 基础函数配置
|
|
import psycopg2
|
|
import pandas as pd
|
|
import calendar
|
|
import datetime
|
|
import pandas as pd
|
|
import requests
|
|
from pathlib import Path
|
|
from urllib.parse import quote
|
|
import json
|
|
import numpy as np
|
|
import time
|
|
from decimal import Decimal
|
|
# 获得连接
|
|
conn = psycopg2.connect(database="f6_bi", user="BASIC$ro_caowei", password="!ro_caowei123", host="hgprecn-cn-nif1vnv0y002-cn-shanghai.hologres.aliyuncs.com", port="80")
|
|
# 获得游标对象,一个游标对象可以对数据库进行执行操作
|
|
cursor = conn.cursor()
|
|
# sql语句 建表
|
|
sql =f"""SELECT * FROM "public"."holo_ads_report_sales_saas_to_renew_org_summary_income_d" WHERE "pt" >= '20230101';"""
|
|
# 执行语句
|
|
cursor.execute(sql)
|
|
# 获取结果集的每一行
|
|
rows = cursor.fetchall()
|
|
# 获取所有字段名
|
|
all_fields = cursor.description
|
|
#执行结果转化为dataframe
|
|
col = []
|
|
for i in all_fields:
|
|
col.append(i[0])
|
|
data_details = pd.DataFrame(list(rows),columns=col)
|
|
# data_details.to_excel(r'C:\Users\admin\Desktop\holo_ads_report_sales_saas_to_renew_org_summary_income_d.xlsx')
|
|
# 关闭数据库连接
|
|
cursor.close()
|
|
conn.close()
|
|
|
|
data_details['version_amount_total'] = data_details['version_amount_total'].apply(lambda x: float(x) if isinstance(x, Decimal) else x)
|
|
data_details['unversion_amount_total'] = data_details['unversion_amount_total'].apply(lambda x: float(x) if isinstance(x, Decimal) else x)
|
|
data_details['irregular_amount_total'] = data_details['irregular_amount_total'].apply(lambda x: float(x) if isinstance(x, Decimal) else x)
|
|
|
|
selected_fields = ['date_fmt', 'version_amount_total', 'unversion_amount_total', 'irregular_amount_total', 'area_manager', 'region_name']
|
|
new_df_data = data_details[selected_fields]
|
|
df = new_df_data.copy()
|
|
df['all_result_d'] = df[['version_amount_total', 'unversion_amount_total', 'irregular_amount_total']].sum(axis=1)
|
|
# df['frequently_result_d'] = df[['version_amount_total', 'unversion_amount_total']].sum(axis=1)
|
|
result_molecule = df[df['area_manager'].notnull() & df['region_name'].notnull() & df['date_fmt'].notnull()].groupby(['date_fmt','area_manager', 'region_name'])['all_result_d'].sum().reset_index()
|
|
result_molecule
|
|
|
|
# 获得连接
|
|
conn = psycopg2.connect(database="f6_bi", user="BASIC$ro_caowei", password="!ro_caowei123", host="hgprecn-cn-nif1vnv0y002-cn-shanghai.hologres.aliyuncs.com", port="80")
|
|
# 获得游标对象,一个游标对象可以对数据库进行执行操作
|
|
cursor = conn.cursor()
|
|
|
|
# sql语句 建表
|
|
sql =f"""SELECT * FROM "public"."holo_ads_report_sales_saas_to_renew_org_regular_income_d" WHERE "pt" >= '20230101';"""
|
|
# 执行语句
|
|
cursor.execute(sql)
|
|
# 获取结果集的每一行
|
|
rows = cursor.fetchall()
|
|
# 获取所有字段名
|
|
all_fields = cursor.description
|
|
#执行结果转化为dataframe
|
|
col = []
|
|
for i in all_fields:
|
|
col.append(i[0])
|
|
data_details = pd.DataFrame(list(rows),columns=col)
|
|
# data_details.to_excel(r'C:\Users\admin\Desktop\holo_ads_report_sales_saas_to_renew_org_regular_income_d.xlsx')
|
|
# 关闭数据库连接
|
|
cursor.close()
|
|
conn.close()
|
|
|
|
selected_fields = ['date_fmt', 'version_amount_total', 'area_manager', 'region_name']
|
|
data_details['date_fmt'] = data_details['date_fmt'].str.slice(0, 6)
|
|
new_df_data = data_details[selected_fields]
|
|
df = new_df_data.copy()
|
|
|
|
# df['all_result_d'] = df[['version_amount_total', 'unversion_amount_total', 'irregular_amount_total']].sum(axis=1)
|
|
# df['frequently_result_d'] = df[['version_amount_total', 'unversion_amount_total']].sum(axis=1)
|
|
result_denominator = df[df['area_manager'].notnull() & df['region_name'].notnull() & df['date_fmt'].notnull()].groupby(['date_fmt','area_manager', 'region_name'])['version_amount_total'].sum().reset_index()
|
|
result_new = pd.merge(result_molecule, result_denominator, on=['date_fmt','area_manager', 'region_name'], how='left')
|
|
result_new['percentage'] = result_new['all_result_d'].astype(int) / result_new['version_amount_total']
|
|
result_new['all_result_d'] = round(result_new['all_result_d'], 2)
|
|
result_new['version_amount_total'] = result_new['version_amount_total'].astype(float).round(2)
|
|
result_new['percentage'] = result_new['percentage'].astype(float).round(2)/100
|
|
# 删除percentage列为空的行
|
|
result_new = result_new.dropna(subset=['percentage'])
|
|
# 重置索引
|
|
result_new = result_new.reset_index(drop=True)
|
|
# result_new.to_excel(r"C:\Users\admin\Desktop\SaaS续费率_区域续费率.xlsx")
|
|
|
|
def generateToken() -> str:
|
|
""" 生成 token """
|
|
|
|
token_api = 'https://api.dingtalk.com/v1.0/oauth2/accessToken'
|
|
|
|
# 该信息在钉钉开放应用中
|
|
data = {
|
|
"appKey": "ding5kqocon5s9oph5uq",
|
|
"appSecret": 'HL1jgsIIfLAC0eTH0A1m4mwxUDqbgsiPeCCGGE3ocM6qJBTIW7Ivt9drxF_Z4Kb_'
|
|
}
|
|
|
|
res = requests.post(token_api, json=data)
|
|
token = res.json()['accessToken']
|
|
|
|
return token
|
|
|
|
def read_instances(token, formUuid, page, n):
|
|
""" 函数功能:读取普通表单的所有数据 """
|
|
|
|
api = f'https://api.dingtalk.com//v1.0/yida/forms/instances/search'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": token
|
|
}
|
|
|
|
formData = {
|
|
"appType" : "APP_UYZ0KG6L0CCNV80GZ66O",
|
|
"systemToken" : "XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2",
|
|
"userId" : "yida_pub_account",
|
|
"language" : "zh_CN",
|
|
"formUuid" : formUuid,
|
|
"currentPage" : page,
|
|
"pageSize" : n
|
|
}
|
|
|
|
res = requests.post(api, headers=headers, json=formData)
|
|
return res.json()
|
|
|
|
def read_delete(token, formInstanceId):
|
|
""" 函数功能:调用本接口删除表单数据。 """
|
|
|
|
api = f'https://api.dingtalk.com//v1.0/yida/forms/instances'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": token
|
|
}
|
|
|
|
formData = {
|
|
"appType" : "APP_UYZ0KG6L0CCNV80GZ66O",
|
|
"systemToken" : "XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2",
|
|
"userId" : "yida_pub_account",
|
|
"language" : "zh_CN",
|
|
"formInstanceId" : formInstanceId
|
|
}
|
|
|
|
res = requests.delete(api, headers=headers, json=formData)
|
|
return res.json()
|
|
|
|
def read_new(FORMID,formData):
|
|
""" 通过实例id 获取表单内容 """
|
|
api = f'https://api.dingtalk.com/v1.0/yida/forms/instances'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": TOKEN
|
|
}
|
|
payload = {
|
|
"formUuid" : FORMID,
|
|
"appType" : "APP_UYZ0KG6L0CCNV80GZ66O",
|
|
"formDataJson" : json.dumps(formData, cls=NpEncoder),
|
|
"systemToken" : "XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2",
|
|
"language" : "zh_CN",
|
|
"userId" : "yida_pub_account"
|
|
}
|
|
|
|
res = requests.post(api, headers=headers, json=payload)
|
|
print(res.json())
|
|
|
|
return res.json()
|
|
|
|
|
|
def component(FORMID,TOKEN):
|
|
""" 获取组件信息 """
|
|
api = f'https://api.dingtalk.com//v1.0/yida/forms/formFields'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": TOKEN
|
|
}
|
|
payload = {
|
|
"formUuid" : FORMID,
|
|
"appType" : "APP_UYZ0KG6L0CCNV80GZ66O",
|
|
# "formDataJson" : json.dumps(formData, cls=NpEncoder),
|
|
"systemToken" : "XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2",
|
|
# "language" : "zh_CN",
|
|
"userId" : "yida_pub_account"
|
|
}
|
|
|
|
res = requests.get(api, headers=headers, json=payload)
|
|
|
|
return res.json()
|
|
def Batch_creation(FORMID,TOKEN,ALL_formData):
|
|
""" 获取组件信息 """
|
|
api = f'https://api.dingtalk.com//v1.0/yida/forms/instances/batchSave'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": TOKEN
|
|
}
|
|
payload = {
|
|
# "formDataJson" : json.dumps(formData, cls=NpEncoder),
|
|
"noExecuteExpression" : "true",
|
|
"formUuid" : FORMID,
|
|
"appType" : "APP_UYZ0KG6L0CCNV80GZ66O",
|
|
"asynchronousExecution" : "true",
|
|
"systemToken" : "XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2",
|
|
"keepRunningAfterException" : "true",
|
|
"userId" : "yida_pub_account",
|
|
"formDataJsonList" : json.dumps(ALL_formData, cls=NpEncoder),
|
|
}
|
|
|
|
res = requests.post(api, headers=headers, json=payload)
|
|
return res.json()
|
|
|
|
def delete_in_batches(FORMID,TOKEN,ALL_DATA_instance):
|
|
""" 批量删除表单实例 """
|
|
api = f'https://api.dingtalk.com//v1.0/yida/forms/instances/batchRemove'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": TOKEN
|
|
}
|
|
|
|
payload = {
|
|
"formUuid" : FORMID,
|
|
"appType" : "APP_UYZ0KG6L0CCNV80GZ66O",
|
|
"asynchronousExecution" : "true",
|
|
"systemToken" : "XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2",
|
|
"formInstanceIdList" : json.dumps(ALL_DATA_instance, cls=NpEncoder),
|
|
"userId" : "yida_pub_account",
|
|
"executeExpression" : "false" # 不触发
|
|
}
|
|
|
|
res = requests.post(api, headers=headers, json=payload)
|
|
return res.json()
|
|
|
|
def delete_in(TOKEN,formInstanceIdList):
|
|
""" 逐条删除表单实例 """
|
|
api = f'https://api.dingtalk.com//v1.0/yida/forms/instances?appType=APP_UYZ0KG6L0CCNV80GZ66O&systemToken=XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2&userId=yida_pub_account&language=zh_CN&formInstanceId={formInstanceIdList}'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": TOKEN
|
|
}
|
|
res = requests.delete(api, headers=headers)
|
|
return res.json()
|
|
|
|
class NpEncoder(json.JSONEncoder):
|
|
def default(self, obj):
|
|
if isinstance(obj, np.integer):
|
|
return int(obj)
|
|
elif isinstance(obj, np.floating):
|
|
return float(obj)
|
|
elif isinstance(obj, np.ndarray):
|
|
return obj.tolist()
|
|
else:
|
|
return super(NpEncoder, self).default(obj)
|
|
TOKEN = generateToken()
|
|
'''读取员工对应关系:宜搭员工-ID对应表 '''
|
|
FORMID = "FORM-EA866E715PF9YA7ECCAGSABX91Q72PVA3WRFL6" # 宜搭员工-ID对应表 FORM-EA866E715PF9YA7ECCAGSABX91Q72PVA3WRFL6
|
|
# 读取流程表单数据
|
|
form_data = read_instances(token=TOKEN, formUuid=FORMID, page=1, n=100)
|
|
PAGES = form_data.get('totalCount')//10 + 1
|
|
ALL_DATA_staff = {}
|
|
""" 获取全量数据 """
|
|
for i in range(1, PAGES+1):
|
|
# form_data = read_processes_instances(token=TOKEN, formUuid=FORMID, createFromTimeGMT=CREATE_FROM, createToTimeGMT=CREATE_TO, page=i, n=100, searchField={'textField_l7if5ff9': '否'})
|
|
form_data = read_instances(token=TOKEN, formUuid=FORMID, page=i, n=100)
|
|
for data in form_data.get('data'):
|
|
ALL_DATA_staff[data['formData']['textField_lfrw3u58']]=data['formData']['textField_lfrw3u59']
|
|
|
|
# '''批量删除区域续费率数据'''
|
|
for i in range(0,10):
|
|
default = True
|
|
while default:
|
|
FORMID = "FORM-TD966Z810ILCWMTI9IWFF6V83NSO3OT1TO7KL1"
|
|
form_data = read_instances(token=TOKEN, formUuid=FORMID, page=1, n=100)
|
|
PAGES = form_data.get('totalCount')//100 +1
|
|
print(form_data.get('totalCount'))
|
|
if form_data.get('totalCount')<=0:
|
|
default = False
|
|
for i in range(PAGES, 1,-1):
|
|
ALL_DATA_instance = []
|
|
form_data = read_instances(token=TOKEN, formUuid=FORMID, page=1, n=100)
|
|
for data in form_data.get('data'):
|
|
ALL_DATA_instance.append(data['formInstanceId'])
|
|
print(f'读取到表单中 {len(ALL_DATA_instance)} 条数据!')
|
|
red_delete = delete_in_batches(FORMID,TOKEN,ALL_DATA_instance)
|
|
form_data = read_instances(token=TOKEN, formUuid=FORMID, page=1, n=100)
|
|
for data in form_data.get('data'):
|
|
formInstanceId = data['formInstanceId']
|
|
delete_in(TOKEN,formInstanceId)
|
|
print(f'单条删除 {formInstanceId} 数据!')
|
|
|
|
'''遍历数据进行新建'''
|
|
data_details = result_new.copy()
|
|
data_details = data_details.astype('string')
|
|
data_details = data_details.fillna('',inplace=False)
|
|
for a in range(0,len(data_details["date_fmt"]),100):
|
|
ALL_formData = []
|
|
for i in range(a,a+100): # for i in range(len(data_NGV["date_fmt"])):
|
|
try:
|
|
formData = {
|
|
'textField_lk7ot5i8':data_details["date_fmt"][i],#"date_fmt"
|
|
# 'employeeField_lk7ot5ig':data_details["area_manager"][i],#"area_manager"
|
|
'textField_lk7ot5ia':data_details["region_name"][i],#"region_name"
|
|
'textField_lk7ot5ib':data_details["all_result_d"][i],#"all_result_d"
|
|
'textField_lk7ot5ic':data_details["version_amount_total"][i],#"version_amount_total"
|
|
'textField_lk7ot5id':data_details["percentage"][i],#"percentage"
|
|
}
|
|
try:
|
|
formData['employeeField_lk7ot5ig'] = ALL_DATA_staff[data_details["area_manager"][i]]
|
|
except:
|
|
formData['employeeField_lk7ot5ig'] = ""
|
|
|
|
ALL_formData.append(json.dumps(formData, cls=NpEncoder))
|
|
except:
|
|
pass
|
|
FORMID = "FORM-TD966Z810ILCWMTI9IWFF6V83NSO3OT1TO7KL1"
|
|
res_new = Batch_creation(FORMID,TOKEN,ALL_formData)
|
|
print("新建第",i,"条数据!",res_new)
|
|
time.sleep(10)
|
|
|
|
'''校验是否新建正常'''
|
|
time.sleep(120)
|
|
FORMID = "FORM-TD966Z810ILCWMTI9IWFF6V83NSO3OT1TO7KL1"
|
|
form_data = read_instances(token=TOKEN, formUuid=FORMID, page=1, n=100)
|
|
if int(form_data.get('totalCount')) ==len(data_details):
|
|
print("数据新建成功!")
|
|
else:
|
|
|
|
def start_instance_process(token: str, name):
|
|
|
|
"""发送宜搭表单 -- 发起流程表单
|
|
|
|
Args:
|
|
token
|
|
data:需要发送的数据字典
|
|
"""
|
|
|
|
yida_api = "https://api.dingtalk.com/v1.0/yida/processes/instances/start"
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": token
|
|
}
|
|
|
|
send_data = {
|
|
"textField_l9fe0uiw": name,
|
|
"textField_l9fe0uiv": name
|
|
}
|
|
|
|
payload = {
|
|
"appType": "APP_TNVBVZ3K8G56HG03Z45Q",
|
|
"systemToken": "CH7669818R0WN18TYTYJ42PE6GY22WZN0BYWKD1",
|
|
"userId": "yida_pub_account",# 超级管理员账号
|
|
"language": "zh_CN",
|
|
"formUuid": "FORM-UX866Q61GNLAZBCIEDF77BGVIIR83K82WYPHLH2",
|
|
"formDataJson": json.dumps(send_data),
|
|
"processCode":"TPROC--UX866Q61GNLAZBCIEDF77BGVIIR83M92WYPHLI2"
|
|
}
|
|
|
|
res = requests.post(yida_api, headers=headers, json=payload)
|
|
return res
|
|
try:
|
|
name = "区域续费率 新建条数不正确!"
|
|
res_yujing = start_instance_process(TOKEN,name)
|
|
except:
|
|
pass
|
|
|
|
|
|
# -*- coding: utf-8 -*-
|
|
# 基础函数配置
|
|
import psycopg2
|
|
import pandas as pd
|
|
import calendar
|
|
import datetime
|
|
import pandas as pd
|
|
import requests
|
|
from pathlib import Path
|
|
from urllib.parse import quote
|
|
import json
|
|
import numpy as np
|
|
import time
|
|
from decimal import Decimal
|
|
# 获得连接
|
|
conn = psycopg2.connect(database="f6_bi", user="BASIC$ro_caowei", password="!ro_caowei123", host="hgprecn-cn-nif1vnv0y002-cn-shanghai.hologres.aliyuncs.com", port="80")
|
|
# 获得游标对象,一个游标对象可以对数据库进行执行操作
|
|
cursor = conn.cursor()
|
|
# sql语句 建表
|
|
sql =f"""SELECT * FROM "public"."holo_ads_report_sales_saas_to_renew_org_summary_income_d" WHERE "pt" >= '20230101';"""
|
|
# 执行语句
|
|
cursor.execute(sql)
|
|
# 获取结果集的每一行
|
|
rows = cursor.fetchall()
|
|
# 获取所有字段名
|
|
all_fields = cursor.description
|
|
#执行结果转化为dataframe
|
|
col = []
|
|
for i in all_fields:
|
|
col.append(i[0])
|
|
data_details = pd.DataFrame(list(rows),columns=col)
|
|
# data_NGV.to_excel(r'C:\Users\admin\Desktop\NGV明细.xlsx')
|
|
# 关闭数据库连接
|
|
cursor.close()
|
|
conn.close()
|
|
|
|
data_details['version_amount_total'] = data_details['version_amount_total'].apply(lambda x: float(x) if isinstance(x, Decimal) else x)
|
|
data_details['unversion_amount_total'] = data_details['unversion_amount_total'].apply(lambda x: float(x) if isinstance(x, Decimal) else x)
|
|
data_details['irregular_amount_total'] = data_details['irregular_amount_total'].apply(lambda x: float(x) if isinstance(x, Decimal) else x)
|
|
|
|
selected_fields = ['date_fmt', 'version_amount_total', 'unversion_amount_total', 'irregular_amount_total', 'service_impl_principal']
|
|
new_df_data = data_details[selected_fields]
|
|
df = new_df_data.copy()
|
|
df['all_result_d'] = df[['version_amount_total', 'unversion_amount_total', 'irregular_amount_total']].sum(axis=1)
|
|
# df['frequently_result_d'] = df[['version_amount_total', 'unversion_amount_total']].sum(axis=1)
|
|
result_molecule = df[df['service_impl_principal'].notnull() & df['date_fmt'].notnull()].groupby(['date_fmt','service_impl_principal'])['all_result_d'].sum().reset_index()
|
|
result_molecule
|
|
|
|
# 获得连接
|
|
conn = psycopg2.connect(database="f6_bi", user="BASIC$ro_caowei", password="!ro_caowei123", host="hgprecn-cn-nif1vnv0y002-cn-shanghai.hologres.aliyuncs.com", port="80")
|
|
# 获得游标对象,一个游标对象可以对数据库进行执行操作
|
|
cursor = conn.cursor()
|
|
|
|
# sql语句 建表
|
|
sql =f"""SELECT * FROM "public"."holo_ads_report_sales_saas_to_renew_org_regular_income_d" WHERE "pt" >= '20230101';"""
|
|
# 执行语句
|
|
cursor.execute(sql)
|
|
# 获取结果集的每一行
|
|
rows = cursor.fetchall()
|
|
# 获取所有字段名
|
|
all_fields = cursor.description
|
|
#执行结果转化为dataframe
|
|
col = []
|
|
for i in all_fields:
|
|
col.append(i[0])
|
|
data_details = pd.DataFrame(list(rows),columns=col)
|
|
# data_NGV.to_excel(r'C:\Users\admin\Desktop\NGV明细.xlsx')
|
|
# 关闭数据库连接
|
|
cursor.close()
|
|
conn.close()
|
|
|
|
data_details['version_amount_total'] = data_details['version_amount_total'].apply(lambda x: float(x) if isinstance(x, Decimal) else x)
|
|
|
|
selected_fields = ['date_fmt', 'version_amount_total', 'service_impl_principal']
|
|
data_details['date_fmt'] = data_details['date_fmt'].str.slice(0, 6)
|
|
new_df_data = data_details[selected_fields]
|
|
df = new_df_data.copy()
|
|
# df['all_result_d'] = df[['version_amount_total', 'unversion_amount_total', 'irregular_amount_total']].sum(axis=1)
|
|
# df['frequently_result_d'] = df[['version_amount_total', 'unversion_amount_total']].sum(axis=1)
|
|
result_denominator = df[df['service_impl_principal'].notnull() & df['date_fmt'].notnull()].groupby(['date_fmt','service_impl_principal'])['version_amount_total'].sum().reset_index()
|
|
result_denominator
|
|
result_new = pd.merge(result_molecule, result_denominator, on=['date_fmt','service_impl_principal'], how='left')
|
|
result_new['percentage'] = result_new['all_result_d'] / result_new['version_amount_total'] * 100
|
|
result_new_A = result_new.copy()
|
|
|
|
# 获得连接
|
|
conn = psycopg2.connect(database="f6_bi", user="BASIC$ro_caowei", password="!ro_caowei123", host="hgprecn-cn-nif1vnv0y002-cn-shanghai.hologres.aliyuncs.com", port="80")
|
|
# 获得游标对象,一个游标对象可以对数据库进行执行操作
|
|
cursor = conn.cursor()
|
|
|
|
# sql语句 建表
|
|
sql =f"""SELECT * FROM "public"."holo_ads_report_sales_saas_regular_income_snapshot_m" WHERE "pt" >= '202301';"""
|
|
# 执行语句
|
|
cursor.execute(sql)
|
|
# 获取结果集的每一行
|
|
rows = cursor.fetchall()
|
|
# 获取所有字段名
|
|
all_fields = cursor.description
|
|
#执行结果转化为dataframe
|
|
col = []
|
|
for i in all_fields:
|
|
col.append(i[0])
|
|
data_details = pd.DataFrame(list(rows),columns=col)
|
|
# data_NGV.to_excel(r'C:\Users\admin\Desktop\NGV明细.xlsx')
|
|
# 关闭数据库连接
|
|
cursor.close()
|
|
conn.close()
|
|
|
|
selected_fields = ['month_id', 'is_renew', 'service_impl_principal']
|
|
new_df_data = data_details[selected_fields]
|
|
new_df_data_filtration = new_df_data.loc[new_df_data['is_renew'] == 1]
|
|
result_denominator_filtration = new_df_data_filtration[new_df_data_filtration['service_impl_principal'].notnull() & new_df_data_filtration['month_id'].notnull()& new_df_data_filtration['is_renew'].notnull()].groupby(['month_id','service_impl_principal'])['is_renew'].sum().reset_index()
|
|
new_df_data['is_renew'] = new_df_data['is_renew'].replace(0, 1)
|
|
result_denominator = new_df_data[new_df_data['service_impl_principal'].notnull() & new_df_data['month_id'].notnull()& new_df_data['is_renew'].notnull()].groupby(['month_id','service_impl_principal'])['is_renew'].sum().reset_index()
|
|
result_new = pd.merge(result_denominator, result_denominator_filtration, on=['month_id','service_impl_principal'], how='left')
|
|
result_new = result_new.rename(columns={'month_id': 'date_fmt'})
|
|
result_new['is_renew_y'] = result_new['is_renew_y'].replace(np.nan, 0)
|
|
result_new['percentage'] = result_new['is_renew_y'] / result_new['is_renew_x'] * 100
|
|
result_new_B = result_new.copy()
|
|
result_new = pd.merge(result_new_A, result_new_B, on=['date_fmt','service_impl_principal'], how='left')
|
|
result_new['all_result_d'] = round(result_new['all_result_d'], 2)
|
|
result_new['version_amount_total'] = round(result_new['version_amount_total'], 2)
|
|
result_new['percentage_x'] = round(result_new['percentage_x'], 2)
|
|
result_new['is_renew_x'] = round(result_new['is_renew_x'], 2)
|
|
result_new['is_renew_y'] = round(result_new['is_renew_y'], 2)
|
|
result_new['percentage_y'] = round(result_new['percentage_y'], 2)/100
|
|
# result_new.to_excel(r"C:\Users\admin\Desktop\SaaS续费率_全国续费率.xlsx")
|
|
|
|
def generateToken() -> str:
|
|
""" 生成 token """
|
|
|
|
token_api = 'https://api.dingtalk.com/v1.0/oauth2/accessToken'
|
|
|
|
# 该信息在钉钉开放应用中
|
|
data = {
|
|
"appKey": "ding5kqocon5s9oph5uq",
|
|
"appSecret": 'HL1jgsIIfLAC0eTH0A1m4mwxUDqbgsiPeCCGGE3ocM6qJBTIW7Ivt9drxF_Z4Kb_'
|
|
}
|
|
|
|
res = requests.post(token_api, json=data)
|
|
token = res.json()['accessToken']
|
|
|
|
return token
|
|
|
|
def read_instances(token, formUuid, page, n):
|
|
""" 函数功能:读取普通表单的所有数据 """
|
|
|
|
api = f'https://api.dingtalk.com//v1.0/yida/forms/instances/search'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": token
|
|
}
|
|
|
|
formData = {
|
|
"appType" : "APP_UYZ0KG6L0CCNV80GZ66O",
|
|
"systemToken" : "XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2",
|
|
"userId" : "yida_pub_account",
|
|
"language" : "zh_CN",
|
|
"formUuid" : formUuid,
|
|
"currentPage" : page,
|
|
"pageSize" : n
|
|
}
|
|
|
|
res = requests.post(api, headers=headers, json=formData)
|
|
return res.json()
|
|
|
|
def read_delete(token, formInstanceId):
|
|
""" 函数功能:调用本接口删除表单数据。 """
|
|
|
|
api = f'https://api.dingtalk.com//v1.0/yida/forms/instances'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": token
|
|
}
|
|
|
|
formData = {
|
|
"appType" : "APP_UYZ0KG6L0CCNV80GZ66O",
|
|
"systemToken" : "XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2",
|
|
"userId" : "yida_pub_account",
|
|
"language" : "zh_CN",
|
|
"formInstanceId" : formInstanceId
|
|
}
|
|
|
|
res = requests.delete(api, headers=headers, json=formData)
|
|
return res.json()
|
|
|
|
def read_new(FORMID,formData):
|
|
""" 通过实例id 获取表单内容 """
|
|
api = f'https://api.dingtalk.com/v1.0/yida/forms/instances'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": TOKEN
|
|
}
|
|
payload = {
|
|
"formUuid" : FORMID,
|
|
"appType" : "APP_UYZ0KG6L0CCNV80GZ66O",
|
|
"formDataJson" : json.dumps(formData, cls=NpEncoder),
|
|
"systemToken" : "XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2",
|
|
"language" : "zh_CN",
|
|
"userId" : "yida_pub_account"
|
|
}
|
|
|
|
res = requests.post(api, headers=headers, json=payload)
|
|
print(res.json())
|
|
|
|
return res.json()
|
|
|
|
|
|
def component(FORMID,TOKEN):
|
|
""" 获取组件信息 """
|
|
api = f'https://api.dingtalk.com//v1.0/yida/forms/formFields'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": TOKEN
|
|
}
|
|
payload = {
|
|
"formUuid" : FORMID,
|
|
"appType" : "APP_UYZ0KG6L0CCNV80GZ66O",
|
|
# "formDataJson" : json.dumps(formData, cls=NpEncoder),
|
|
"systemToken" : "XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2",
|
|
# "language" : "zh_CN",
|
|
"userId" : "yida_pub_account"
|
|
}
|
|
|
|
res = requests.get(api, headers=headers, json=payload)
|
|
|
|
return res.json()
|
|
def Batch_creation(FORMID,TOKEN,ALL_formData):
|
|
""" 获取组件信息 """
|
|
api = f'https://api.dingtalk.com//v1.0/yida/forms/instances/batchSave'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": TOKEN
|
|
}
|
|
payload = {
|
|
# "formDataJson" : json.dumps(formData, cls=NpEncoder),
|
|
"noExecuteExpression" : "true",
|
|
"formUuid" : FORMID,
|
|
"appType" : "APP_UYZ0KG6L0CCNV80GZ66O",
|
|
"asynchronousExecution" : "true",
|
|
"systemToken" : "XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2",
|
|
"keepRunningAfterException" : "true",
|
|
"userId" : "yida_pub_account",
|
|
"formDataJsonList" : json.dumps(ALL_formData, cls=NpEncoder),
|
|
}
|
|
|
|
res = requests.post(api, headers=headers, json=payload)
|
|
return res.json()
|
|
|
|
def delete_in_batches(FORMID,TOKEN,ALL_DATA_instance):
|
|
""" 批量删除表单实例 """
|
|
api = f'https://api.dingtalk.com//v1.0/yida/forms/instances/batchRemove'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": TOKEN
|
|
}
|
|
|
|
payload = {
|
|
"formUuid" : FORMID,
|
|
"appType" : "APP_UYZ0KG6L0CCNV80GZ66O",
|
|
"asynchronousExecution" : "true",
|
|
"systemToken" : "XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2",
|
|
"formInstanceIdList" : json.dumps(ALL_DATA_instance, cls=NpEncoder),
|
|
"userId" : "yida_pub_account",
|
|
"executeExpression" : "false" # 不触发
|
|
}
|
|
|
|
res = requests.post(api, headers=headers, json=payload)
|
|
return res.json()
|
|
|
|
def delete_in(TOKEN,formInstanceIdList):
|
|
""" 逐条删除表单实例 """
|
|
api = f'https://api.dingtalk.com//v1.0/yida/forms/instances?appType=APP_UYZ0KG6L0CCNV80GZ66O&systemToken=XA966F81JAJOFCVVVKO64E9MIIZV1EWE5SFMKJ2&userId=yida_pub_account&language=zh_CN&formInstanceId={formInstanceIdList}'
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": TOKEN
|
|
}
|
|
res = requests.delete(api, headers=headers)
|
|
return res.json()
|
|
|
|
class NpEncoder(json.JSONEncoder):
|
|
def default(self, obj):
|
|
if isinstance(obj, np.integer):
|
|
return int(obj)
|
|
elif isinstance(obj, np.floating):
|
|
return float(obj)
|
|
elif isinstance(obj, np.ndarray):
|
|
return obj.tolist()
|
|
else:
|
|
return super(NpEncoder, self).default(obj)
|
|
TOKEN = generateToken()
|
|
'''读取员工对应关系:宜搭员工-ID对应表 '''
|
|
FORMID = "FORM-EA866E715PF9YA7ECCAGSABX91Q72PVA3WRFL6" # 宜搭员工-ID对应表 FORM-EA866E715PF9YA7ECCAGSABX91Q72PVA3WRFL6
|
|
# 读取流程表单数据
|
|
form_data = read_instances(token=TOKEN, formUuid=FORMID, page=1, n=100)
|
|
PAGES = form_data.get('totalCount')//10 + 1
|
|
ALL_DATA_staff = {}
|
|
""" 获取全量数据 """
|
|
for i in range(1, PAGES+1):
|
|
# form_data = read_processes_instances(token=TOKEN, formUuid=FORMID, createFromTimeGMT=CREATE_FROM, createToTimeGMT=CREATE_TO, page=i, n=100, searchField={'textField_l7if5ff9': '否'})
|
|
form_data = read_instances(token=TOKEN, formUuid=FORMID, page=i, n=100)
|
|
for data in form_data.get('data'):
|
|
ALL_DATA_staff[data['formData']['textField_lfrw3u58']]=data['formData']['textField_lfrw3u59']
|
|
|
|
# '''批量删除全国续费率数据'''
|
|
for i in range(0,10):
|
|
default = True
|
|
while default:
|
|
FORMID = "FORM-L8966281FILCMAXK7QDGW5E0SZ3Y2CAJHP7KL1"
|
|
form_data = read_instances(token=TOKEN, formUuid=FORMID, page=1, n=100)
|
|
PAGES = form_data.get('totalCount')//100 +1
|
|
print(form_data.get('totalCount'))
|
|
if form_data.get('totalCount')<=0:
|
|
default = False
|
|
for i in range(PAGES, 1,-1):
|
|
ALL_DATA_instance = []
|
|
form_data = read_instances(token=TOKEN, formUuid=FORMID, page=1, n=100)
|
|
for data in form_data.get('data'):
|
|
ALL_DATA_instance.append(data['formInstanceId'])
|
|
print(f'读取到表单中 {len(ALL_DATA_instance)} 条数据!')
|
|
red_delete = delete_in_batches(FORMID,TOKEN,ALL_DATA_instance)
|
|
form_data = read_instances(token=TOKEN, formUuid=FORMID, page=1, n=100)
|
|
for data in form_data.get('data'):
|
|
formInstanceId = data['formInstanceId']
|
|
delete_in(TOKEN,formInstanceId)
|
|
print(f'单条删除 {formInstanceId} 数据!')
|
|
|
|
'''遍历数据进行新建'''
|
|
data_details = result_new.copy()
|
|
data_details = data_details.astype('string')
|
|
data_details = data_details.fillna('',inplace=False)
|
|
for a in range(0,len(data_details["date_fmt"]),100):
|
|
ALL_formData = []
|
|
for i in range(a,a+100): # for i in range(len(data_NGV["date_fmt"])):
|
|
try:
|
|
formData = {
|
|
'textField_lk7pibrx':data_details["date_fmt"][i],#"date_fmt"
|
|
# 'employeeField_lk7pibs5':data_details["service_impl_principal"][i],#"service_impl_principal"
|
|
'textField_lk7pibrz':data_details["all_result_d"][i],#"all_result_d"
|
|
'textField_lk7pibs0':data_details["version_amount_total"][i],#"version_amount_total"
|
|
'textField_lk7pibs1':data_details["percentage_x"][i],#"percentage_x"
|
|
'textField_lk7pibs2':data_details["is_renew_x"][i],#"is_renew_x"
|
|
'textField_lk7pibs3':data_details["is_renew_y"][i],#"is_renew_y"
|
|
'textField_lk7pibs4':data_details["percentage_y"][i],#"percentage_y"
|
|
}
|
|
try:
|
|
formData['employeeField_lk7pibs5'] = ALL_DATA_staff[data_details["service_impl_principal"][i]]
|
|
except:
|
|
formData['employeeField_lk7pibs5'] = ""
|
|
|
|
ALL_formData.append(json.dumps(formData, cls=NpEncoder))
|
|
except:
|
|
pass
|
|
FORMID = "FORM-L8966281FILCMAXK7QDGW5E0SZ3Y2CAJHP7KL1"
|
|
res_new = Batch_creation(FORMID,TOKEN,ALL_formData)
|
|
print("新建第",i,"条数据!",res_new)
|
|
time.sleep(10)
|
|
|
|
'''校验是否新建正常'''
|
|
time.sleep(120)
|
|
FORMID = "FORM-L8966281FILCMAXK7QDGW5E0SZ3Y2CAJHP7KL1"
|
|
form_data = read_instances(token=TOKEN, formUuid=FORMID, page=1, n=100)
|
|
if int(form_data.get('totalCount')) ==len(data_details):
|
|
print("数据新建成功!")
|
|
else:
|
|
|
|
def start_instance_process(token: str, name):
|
|
|
|
"""发送宜搭表单 -- 发起流程表单
|
|
|
|
Args:
|
|
token
|
|
data:需要发送的数据字典
|
|
"""
|
|
|
|
yida_api = "https://api.dingtalk.com/v1.0/yida/processes/instances/start"
|
|
|
|
headers = {
|
|
"Content-Type": "application/json",
|
|
"x-acs-dingtalk-access-token": token
|
|
}
|
|
|
|
send_data = {
|
|
"textField_l9fe0uiw": name,
|
|
"textField_l9fe0uiv": name
|
|
}
|
|
|
|
payload = {
|
|
"appType": "APP_TNVBVZ3K8G56HG03Z45Q",
|
|
"systemToken": "CH7669818R0WN18TYTYJ42PE6GY22WZN0BYWKD1",
|
|
"userId": "yida_pub_account",# 超级管理员账号
|
|
"language": "zh_CN",
|
|
"formUuid": "FORM-UX866Q61GNLAZBCIEDF77BGVIIR83K82WYPHLH2",
|
|
"formDataJson": json.dumps(send_data),
|
|
"processCode":"TPROC--UX866Q61GNLAZBCIEDF77BGVIIR83M92WYPHLI2"
|
|
}
|
|
|
|
res = requests.post(yida_api, headers=headers, json=payload)
|
|
return res
|
|
try:
|
|
name = "全国续费率 新建条数不正确!"
|
|
res_yujing = start_instance_process(TOKEN,name)
|
|
except:
|
|
pass |