From 55f5f65e153909f96bd8155c3d9009dd6593ef7c Mon Sep 17 00:00:00 2001 From: youngS Date: Sun, 5 Dec 2021 13:55:47 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BF=AE=E5=A4=8D=E5=B7=B2=E7=9F=A5=E9=97=AE?= =?UTF-8?q?=E9=A2=98=EF=BC=8C=E5=A2=9E=E5=8A=A0=E8=AE=BE=E5=A4=87=E6=B6=88?= =?UTF-8?q?=E5=8C=96=E7=BB=9F=E8=AE=A1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/components/user/FirSuperSignBase.vue | 130 +++++++++++++++++- fir_client/src/restful/index.js | 15 ++ fir_ser/api/urls.py | 3 +- fir_ser/api/utils/apple/appleapiv3.py | 8 +- fir_ser/api/views/supersign.py | 48 ++++++- 5 files changed, 197 insertions(+), 7 deletions(-) diff --git a/fir_client/src/components/user/FirSuperSignBase.vue b/fir_client/src/components/user/FirSuperSignBase.vue index 1b38a4a..97b5e35 100644 --- a/fir_client/src/components/user/FirSuperSignBase.vue +++ b/fir_client/src/components/user/FirSuperSignBase.vue @@ -722,6 +722,65 @@ + + + + + + + 搜索 + + + + + + + + + + + + + +
-import {developercert, DeviceBillInfo, iosdeveloper, iosdevices, iosdevicesudid, iosudevices} from "@/restful"; +import { + developercert, + DeviceBillInfo, + DeviceRankInfo, + iosdeveloper, + iosdevices, + iosdevicesudid, + iosudevices +} from "@/restful"; import {getUserInfoFun, removeAaary} from "@/utils"; export default { @@ -757,12 +824,15 @@ export default { app_developer_lists: [], app_devices_lists: [], app_bill_lists: [], + app_rank_lists: [], app_bill_info_lists: [], app_udid_lists: [], activeName: "iosdeveloper", udidsearch: "", Bundleidsearch: "", appidseach: "", + appnamesearch: "", + timerangesearch: [], dialogaddDeveloperVisible: false, importcertDeveloperVisible: false, title: "", @@ -778,6 +848,40 @@ export default { loadingfun: {}, loading: false, cert_pwd: '', + pickerOptions: { + shortcuts: [{ + text: '今天', + onClick(picker) { + const end = new Date(); + const start = new Date(); + picker.$emit('pick', [start, end]); + } + }, { + text: '最近一周', + onClick(picker) { + const end = new Date(); + const start = new Date(); + start.setTime(start.getTime() - 3600 * 1000 * 24 * 7); + picker.$emit('pick', [start, end]); + } + }, { + text: '最近一个月', + onClick(picker) { + const end = new Date(); + const start = new Date(); + start.setTime(start.getTime() - 3600 * 1000 * 24 * 30); + picker.$emit('pick', [start, end]); + } + }, { + text: '最近三个月', + onClick(picker) { + const end = new Date(); + const start = new Date(); + start.setTime(start.getTime() - 3600 * 1000 * 24 * 90); + picker.$emit('pick', [start, end]); + } + }] + }, } }, watch: { 'dialogaddDeveloperVisible': function () { @@ -1009,6 +1113,11 @@ export default { }); }); }, + show_device_uinfo(bundle_id) { + this.Bundleidsearch = bundle_id; + this.activeName = 'useddevices' + this.get_data_from_tabname(this.activeName); + }, get_data_from_tabname(tabname, data = {}) { data.udid = this.udidsearch.replace(/^\s+|\s+$/g, ""); data.bundleid = this.Bundleidsearch.replace(/^\s+|\s+$/g, ""); @@ -1026,6 +1135,13 @@ export default { this.iosdeveloperFun({"methods": "GET", "data": data}) } else if (tabname === "devicesbill") { this.iosdevicebillFun({"methods": "GET", "data": data}) + } else if (tabname === "devicesrank") { + if (this.timerangesearch && this.timerangesearch.length === 2) { + data.start_time = this.timerangesearch[0]; + data.end_time = this.timerangesearch[1]; + } + data.appnamesearch = this.appnamesearch.replace(/^\s+|\s+$/g, ""); + this.iosdevicerankFun({"methods": "GET", "data": data}) } else if (tabname === "iosudevices") { this.iosudevicesFun("GET", data, null) } @@ -1149,6 +1265,18 @@ export default { this.loading = false }, params) }, + iosdevicerankFun(params) { + this.loading = true; + DeviceRankInfo(data => { + if (data.code === 1000) { + this.app_rank_lists = data.data; + this.pagination.total = data.count; + } else { + this.$message.error("信息获取失败了 " + data.msg); + } + this.loading = false + }, params) + }, iosdevicesudidFun(action, data, scope) { if (action !== 'GET') { this.loadingfun = this.$loading({ diff --git a/fir_client/src/restful/index.js b/fir_client/src/restful/index.js index d74847a..b3955d4 100644 --- a/fir_client/src/restful/index.js +++ b/fir_client/src/restful/index.js @@ -724,6 +724,21 @@ export function DeviceBillInfo(callBack, params, load = true) { ); } +/**签名下载排行 */ +export function DeviceRankInfo(callBack, params, load = true) { + getData( + params.methods, + USERSEVER + '/supersign/rank', + params.data, + data => { + callBack(data); + }, + load, + true, + true + ); +} + /**应用举报 */ export function appReport(callBack, params, load = true) { getData( diff --git a/fir_ser/api/urls.py b/fir_ser/api/urls.py index 42a5d27..575a6fc 100644 --- a/fir_ser/api/urls.py +++ b/fir_ser/api/urls.py @@ -27,7 +27,7 @@ from api.views.receiveudids import IosUDIDView, TaskView from api.views.report import ReportView from api.views.storage import StorageView from api.views.supersign import DeveloperView, SuperSignUsedView, AppUDIDUsedView, SuperSignCertView, \ - DeviceUsedBillView, DeveloperDeviceView + DeviceUsedBillView, DeveloperDeviceView, DeviceUsedRankInfoView from api.views.thirdlogin import ValidWxChatToken, ThirdWxAccount from api.views.uploads import AppAnalyseView, UploadView @@ -61,6 +61,7 @@ urlpatterns = [ re_path("^supersign/udevices$", DeveloperDeviceView.as_view()), re_path("^supersign/cert$", SuperSignCertView.as_view()), re_path("^supersign/bill$", DeviceUsedBillView.as_view()), + re_path("^supersign/rank$", DeviceUsedRankInfoView.as_view()), re_path("^package_prices$", PriceView.as_view()), re_path("^orders$", OrderView.as_view()), re_path("^certification$", CertificationView.as_view()), diff --git a/fir_ser/api/utils/apple/appleapiv3.py b/fir_ser/api/utils/apple/appleapiv3.py index 3caf78c..71a1cb4 100644 --- a/fir_ser/api/utils/apple/appleapiv3.py +++ b/fir_ser/api/utils/apple/appleapiv3.py @@ -654,9 +654,9 @@ def call_function_try_attempts(try_attempts=3, sleep_time=1): def decorator(func): @wraps(func) def wrapper(*args, **kwargs): - res = False, {} start_time = time.time() flag = False + res = '' for i in range(try_attempts): try: res = func(*args, **kwargs) @@ -666,10 +666,14 @@ def call_function_try_attempts(try_attempts=3, sleep_time=1): logger.warning( f'exec {func} failed. Failed:{e} {try_attempts} times in total. now {sleep_time} later try ' f'again...{i}') + res = str(e) + if 'Authentication credentials are missing or invalid' in str(e): + res = '认证失败,请检查开发者信息填写是否正确' time.sleep(sleep_time) + logger.info(f"exec {func} finished. time:{time.time() - start_time}") if not flag: logger.error(f'exec {func} failed after the maximum number of attempts. Failed:{res}') - logger.info(f"exec {func} finished. time:{time.time() - start_time}") + raise Exception(res) return res return wrapper diff --git a/fir_ser/api/views/supersign.py b/fir_ser/api/views/supersign.py index b2e0e85..7b15e19 100644 --- a/fir_ser/api/views/supersign.py +++ b/fir_ser/api/views/supersign.py @@ -3,6 +3,7 @@ # project: 3月 # author: liuyu # date: 2020/3/4 +import datetime import logging from django.db.models import Count, Q @@ -11,7 +12,8 @@ from rest_framework.pagination import PageNumberPagination from rest_framework.response import Response from rest_framework.views import APIView -from api.models import AppIOSDeveloperInfo, APPSuperSignUsedInfo, AppUDID, IosDeveloperPublicPoolBill, UDIDsyncDeveloper +from api.models import AppIOSDeveloperInfo, APPSuperSignUsedInfo, AppUDID, IosDeveloperPublicPoolBill, \ + UDIDsyncDeveloper from api.utils.app.supersignutils import IosUtils from api.utils.auth import ExpiringTokenAuthentication, SuperSignPermission from api.utils.modelutils import get_user_public_used_sign_num, get_user_public_sign_num @@ -211,8 +213,9 @@ class DeveloperView(APIView): if developer_obj: logger.error(f"user {request.user} delete developer {developer_obj}") - IosUtils.clean_developer(developer_obj, request.user) - IosUtils.revoke_developer_cert(developer_obj, request.user) + if developer_obj.certid: + IosUtils.clean_developer(developer_obj, request.user) + IosUtils.revoke_developer_cert(developer_obj, request.user) developer_obj.delete() return self.get(request) @@ -413,3 +416,42 @@ class DeviceUsedBillView(APIView): 'all_balance': get_user_public_sign_num(request.user) } return Response(res.dict) + + +class DeviceUsedRankInfoView(APIView): + authentication_classes = [ExpiringTokenAuthentication, ] + permission_classes = [SuperSignPermission, ] + + def get(self, request): + res = BaseResponse() + page_obj = PageNumber() + appnamesearch = request.query_params.get("appnamesearch") + start_time = request.query_params.get("start_time") + end_time = request.query_params.get("end_time") + app_used_sign_objs = APPSuperSignUsedInfo.objects.filter(user_id=request.user) + if appnamesearch: + app_used_sign_objs = app_used_sign_objs.filter( + Q(app_id__name=appnamesearch) | Q(app_id__bundle_id=appnamesearch)) + if end_time and start_time: + try: + start_time = datetime.date.fromtimestamp(int(start_time) / 1000) + end_time = datetime.date.fromtimestamp(int(end_time) / 1000 + 24 * 60 * 60 - 1) + app_used_sign_objs = app_used_sign_objs.filter(created_time__range=[start_time, end_time]) + except Exception as e: + logger.error(f"get time range failed {e}") + res.count = app_used_sign_objs.count() + + app_used_sign_objs = app_used_sign_objs.values('app_id__app_id', 'app_id__name', 'app_id__bundle_id').annotate( + count=Count('app_id__app_id')).order_by('-count') + + app_used_sign_infos = page_obj.paginate_queryset(queryset=app_used_sign_objs, + request=request, view=self) + new_app_used_sign_infos = [] + for app_used_info in app_used_sign_infos: + new_app_used_info = {} + for key, value in app_used_info.items(): + new_key = key.replace('app_id__', '') + new_app_used_info[new_key] = value + new_app_used_sign_infos.append(new_app_used_info) + res.data = new_app_used_sign_infos + return Response(res.dict)