303 lines
12 KiB
Python
303 lines
12 KiB
Python
import json
|
|
import random
|
|
import warnings
|
|
from calendar import timegm
|
|
from datetime import datetime
|
|
|
|
import requests
|
|
from django_filters.rest_framework import DjangoFilterBackend
|
|
from openpyxl import Workbook, load_workbook
|
|
from rest_framework import status
|
|
from rest_framework.decorators import action
|
|
from rest_framework.filters import OrderingFilter, SearchFilter
|
|
from rest_framework.permissions import IsAuthenticated
|
|
from rest_framework.response import Response
|
|
from rest_framework.views import APIView
|
|
from rest_framework.viewsets import ModelViewSet
|
|
from rest_framework_jwt.authentication import JSONWebTokenAuthentication
|
|
from rest_framework_jwt.serializers import jwt_encode_handler, jwt_payload_handler
|
|
from rest_framework_jwt.settings import api_settings
|
|
|
|
from crm.zhenzismsclient import ZhenziSmsClient
|
|
from examtest.models_paper import WorkScope
|
|
from question.models import Questioncat
|
|
from question.serializers import QuestionSerializer
|
|
from server import settings
|
|
from utils.custom import CommonPagination
|
|
|
|
from .models import Company, Consumer, PaySubject, SendCode
|
|
from .serializers import CompanySerializer, ConsumerSerializer
|
|
|
|
appid = 'wxf1e9471c93f05ad6'
|
|
secret = '4bf7f9bd6c52634586bbe792a1f0a834'
|
|
sms_appid = '100172'
|
|
sms_appsecret = '00b8681c-0ce6-41c8-a867-904c1891c78a'
|
|
sms_url = 'https://sms.zhenzikj.com'
|
|
|
|
def jwt_payload_handler(user):
|
|
payload = {
|
|
'user_id': user.pk,
|
|
'type':'consumer',
|
|
'exp': datetime.utcnow() + api_settings.JWT_EXPIRATION_DELTA
|
|
}
|
|
if api_settings.JWT_ALLOW_REFRESH:
|
|
payload['orig_iat'] = timegm(
|
|
datetime.utcnow().utctimetuple()
|
|
)
|
|
|
|
if api_settings.JWT_AUDIENCE is not None:
|
|
payload['aud'] = api_settings.JWT_AUDIENCE
|
|
|
|
if api_settings.JWT_ISSUER is not None:
|
|
payload['iss'] = api_settings.JWT_ISSUER
|
|
|
|
return payload
|
|
|
|
class CompanyViewSet(ModelViewSet):
|
|
"""
|
|
客户企业:增删改查
|
|
"""
|
|
perms_map = [
|
|
{'get': 'company_list'}, {'post': 'company_create'},
|
|
{'put': 'company_update'}, {'delete': 'company_delete'}]
|
|
queryset = Company.objects.filter(is_delete=0).all()
|
|
serializer_class = CompanySerializer
|
|
pagination_class = None #不分页
|
|
filter_backends = [DjangoFilterBackend,SearchFilter, OrderingFilter]
|
|
search_fields = ('^name',)
|
|
ordering_fields = ('id',)
|
|
ordering = ['-id']
|
|
|
|
class ConsumerViewSet(ModelViewSet):
|
|
"""
|
|
学员:增删改查
|
|
"""
|
|
perms_map = [
|
|
{'get': 'consumer_list'}, {'post': 'consumer_create'},
|
|
{'put': 'consumer_update'}, {'delete': 'consumer_delete'}]
|
|
queryset = Consumer.objects.filter(is_delete=0).all()
|
|
serializer_class = ConsumerSerializer
|
|
pagination_class = CommonPagination
|
|
ordering_fields = ('id','company','create_time')
|
|
ordering = ['company','-create_time']
|
|
filter_backends = [DjangoFilterBackend, SearchFilter, OrderingFilter]
|
|
filterset_fields = ('company',)
|
|
search_fields = ('^name','^username')
|
|
|
|
def get_queryset(self):
|
|
queryset = self.queryset
|
|
queryset = self.get_serializer_class().setup_eager_loading(queryset)
|
|
return queryset
|
|
|
|
def create(self, request, *args, **kwargs):
|
|
serializer = self.get_serializer(data=request.data)
|
|
if serializer.is_valid():
|
|
instance = serializer.save()
|
|
else:
|
|
return Response(serializer.errors)
|
|
if request.data.get('subjects', None):
|
|
for i in request.data.get('subjects'):
|
|
PaySubject.objects.get_or_create(consumer = instance, subject__id=i, defaults={'consumer':instance,'subject':Questioncat.objects.get(id=i)})
|
|
return Response(serializer.data, status=status.HTTP_201_CREATED)
|
|
|
|
def update(self, request, *args, **kwargs):
|
|
instance = self.get_object()
|
|
serializer = self.get_serializer(instance, data=request.data)
|
|
if serializer.is_valid():
|
|
instance = serializer.save()
|
|
else:
|
|
return Response(serializer.errors)
|
|
PaySubject.objects.filter(consumer = instance).delete()
|
|
if request.data.get('subjects', None):
|
|
for i in request.data.get('subjects'):
|
|
PaySubject.objects.get_or_create(consumer = instance, subject__id=i, defaults={'consumer':instance,'subject':Questioncat.objects.get(id=i)})
|
|
return Response(serializer.data)
|
|
|
|
@action(methods=['get'], detail=False,
|
|
url_path='subjectpaid', url_name='subject_paid',perms_map=[{'*':'my_subject'}])
|
|
def has_paid(self, request):
|
|
"""
|
|
当前登陆消费者已付费的学科
|
|
"""
|
|
queryset = PaySubject.objects.filter(consumer = request.user)
|
|
data = queryset.values_list('subject__id',flat=True)
|
|
return Response(data)
|
|
|
|
@action(methods=['get'], detail=False,
|
|
url_path='sendcode', url_name='code_send',authentication_classes=[],permission_classes=[])
|
|
def sendcode(self, request):
|
|
'''
|
|
发送验证码
|
|
'''
|
|
client = ZhenziSmsClient(sms_url, sms_appid, sms_appsecret)
|
|
code = random.randint(1000,9999)
|
|
phone = request.query_params.get('phone')
|
|
params = {'message':'您的验证码为:' + str(code) +',5分钟内有效', 'number': phone}
|
|
result = json.loads(client.send(params))
|
|
if result['code'] == 0:
|
|
SendCode.objects.create(phone=phone, code=code)
|
|
return Response(status=status.HTTP_200_OK)
|
|
else:
|
|
return Response({'error':result['data']})
|
|
|
|
@action(methods=['post','delete','get'], detail=False,
|
|
url_path='collects', url_name='create_collects', perms_map=[{'*':'my_collects'}])
|
|
def collects(self, request):
|
|
'''
|
|
个人收藏集
|
|
'''
|
|
if request.method == 'POST':
|
|
questionId = request.data.get('question',None)
|
|
if questionId:
|
|
request.user.collects.remove(questionId)
|
|
request.user.collects.add(questionId)
|
|
return Response(status=status.HTTP_200_OK)
|
|
else:
|
|
return Response({'error':'post参数错误'})
|
|
elif request.method == 'GET':
|
|
queryset = request.user.collects.all().order_by('-update_time')
|
|
serializer = QuestionSerializer(instance=queryset,many=True)
|
|
return Response(serializer.data)
|
|
elif request.method == 'DELETE':
|
|
questionId = request.data.get('question',None)
|
|
if questionId:
|
|
request.user.collects.remove(questionId)
|
|
return Response(status=status.HTTP_200_OK)
|
|
else:
|
|
return Response({'error':'delete参数错误'})
|
|
|
|
|
|
@action(methods=['post'], detail=False,
|
|
url_path='import', url_name='import_consumer')
|
|
def import_consumer(self, request):
|
|
"""
|
|
导入用户
|
|
"""
|
|
xlsxpath = request.data['path']
|
|
fullpath = settings.BASE_DIR + xlsxpath
|
|
wb = load_workbook(fullpath)
|
|
sheet = wb.worksheets[0]
|
|
# 验证文件内容
|
|
if sheet['a2'].value != '姓名':
|
|
return Response({"error":"姓名列错误!"})
|
|
if sheet['b2'].value != '账户(手机号)':
|
|
return Response({"error":"账户列错误!"})
|
|
if sheet['c2'].value != '单位':
|
|
return Response({"error":"单位列错误!"})
|
|
if sheet['d2'].value != '工作类别':
|
|
return Response({"error":"工作类别列错误!"})
|
|
companydict = {}
|
|
consumerdict = {}
|
|
companys = Company.objects.filter(is_delete=0)
|
|
for i in companys:
|
|
companydict[i.name] = i.id
|
|
m = 3
|
|
while sheet['B'+str(m)].value:
|
|
name = sheet['A'+str(m)].value
|
|
if name:
|
|
name = name.replace(' ', '')
|
|
username = sheet['B'+str(m)].value
|
|
if username:
|
|
username = str(username).replace(' ', '')
|
|
companyname = sheet['C'+str(m)].value
|
|
if companyname:
|
|
companyname = companyname.replace(' ', '')
|
|
if companyname not in companydict:
|
|
return Response({"error":"不存在单位("+companyname+")!请先新建"})
|
|
else:
|
|
companyobj = Company.objects.get(id=companydict[companyname])
|
|
workscope = sheet['d'+str(m)].value
|
|
if Consumer.objects.filter(username = username).exists():
|
|
obj = Consumer.objects.filter(username = username).first()
|
|
else:
|
|
obj = Consumer()
|
|
obj.username = username
|
|
obj.name = name
|
|
obj.company = companyobj
|
|
obj.is_delete = False
|
|
obj.save()
|
|
if workscope:
|
|
workscope = workscope.replace(' ', '')
|
|
try:
|
|
workscopeobj = WorkScope.objects.get(name=workscope)
|
|
obj.workscope = workscopeobj
|
|
PaySubject.objects.create(subject=workscopeobj.subject, consumer = obj)
|
|
except:
|
|
pass
|
|
obj.save()
|
|
m = m + 1
|
|
return Response(status=status.HTTP_200_OK)
|
|
|
|
@action(methods=['get'], detail=False,
|
|
url_path='export', url_name='export_consumer')
|
|
def export(self, request):
|
|
queryset = self.filter_queryset(self.queryset)
|
|
print(queryset)
|
|
|
|
class ConsumerMPLoginView(APIView):
|
|
"""
|
|
小程序登陆颁发token
|
|
"""
|
|
authentication_classes=[]
|
|
permission_classes=[]
|
|
def post(self, request, *args, **kwargs):
|
|
code = request.data['code']
|
|
info = requests.get('https://api.weixin.qq.com/sns/jscode2session?appid='+appid+'&secret='+secret+'&js_code=' +
|
|
code+'&grant_type=authorization_code').content.decode('utf-8')
|
|
info = json.loads(info)
|
|
openid = info['openid']
|
|
session_key = info['session_key']
|
|
consumer = Consumer.objects.get_or_create(openid = openid)[0]
|
|
serializer = ConsumerSerializer(instance=consumer)
|
|
payload = jwt_payload_handler(consumer)
|
|
token = jwt_encode_handler(payload)
|
|
return Response({"token":token,"session_key":session_key, "openid":openid, "userinfo":serializer.data})
|
|
|
|
class ConsumerLogoutView(APIView):
|
|
authentication_classes = ()
|
|
permission_classes = ()
|
|
def get(self, request, *args, **kwargs):
|
|
return Response(status=status.HTTP_200_OK)
|
|
|
|
class ConsumerRegister(APIView):
|
|
'''
|
|
验证码登陆和注册
|
|
'''
|
|
def post(self, request, *args, **kwargs):
|
|
data = request.data
|
|
phone = data.get('phone', None)
|
|
code = data.get('code', None)
|
|
avatar = data.get('avatar', None)
|
|
nickname = data.get('nickname', None)
|
|
if phone and code:
|
|
obj = SendCode.objects.filter(phone=phone).last()
|
|
if obj:
|
|
if code == obj.code: # 验证通过
|
|
consumer_queryset = Consumer.objects.filter(username=phone)
|
|
if consumer_queryset.exists(): # 是否存在
|
|
consumer = consumer_queryset.first()
|
|
openid = request.user.openid
|
|
request.user.delete(soft=False) # 彻底删除
|
|
consumer.openid = openid
|
|
if avatar and nickname:
|
|
consumer.avatar = avatar
|
|
consumer.nickname = nickname
|
|
consumer.is_delete = False
|
|
consumer.save()
|
|
return Response(status=status.HTTP_200_OK)
|
|
else:
|
|
consumer = request.user
|
|
consumer.username = phone
|
|
if avatar and nickname:
|
|
consumer.avatar = avatar
|
|
consumer.nickname = nickname
|
|
consumer.is_delete = False
|
|
consumer.save()
|
|
return Response(status=status.HTTP_200_OK)
|
|
else:
|
|
return Response({'error':'验证码错误!'})
|
|
else:
|
|
return Response({'error':'认证错误!'})
|
|
else:
|
|
return Response({'error':'信息不全!'})
|