add lensman_oauth page

Brightcells 8 lat temu
rodzic
commit
d0affd4b01

+ 5 - 4
account/admin.py

@@ -10,9 +10,9 @@ from account.models import (LensmanIncomeExpensesInfo, LensmanInfo, LensmanLogin
10 10
 
11 11
 class LensmanInfoAdmin(admin.ModelAdmin):
12 12
     readonly_fields = ('lensman_id', 'encryption', )
13
-    list_display = ('lensman_id', 'username', 'name', 'sex', 'phone', 'location', 'proportion', 'status', 'created_at', 'updated_at')
13
+    list_display = ('lensman_id', 'unionid', 'username', 'name', 'sex', 'phone', 'location', 'proportion', 'balance', 'user_status', 'status', 'created_at', 'updated_at')
14 14
     search_fields = ('name', 'phone', 'location')
15
-    list_filter = ('sex', 'status')
15
+    list_filter = ('sex', 'user_status', 'status')
16 16
 
17 17
     def save_model(self, request, obj, form, change):
18 18
         if not obj.lensman_id:
@@ -20,11 +20,12 @@ class LensmanInfoAdmin(admin.ModelAdmin):
20 20
             obj.lensman_id = user_id
21 21
 
22 22
         fields = {
23
+            'unionid': obj.unionid,
23 24
             'name': obj.name,
24 25
             'sex': obj.sex,
25 26
             'phone': obj.phone,
26 27
             'location': obj.location,
27
-            'user_status': obj.status,
28
+            'user_status': obj.user_status,
28 29
         }
29 30
         user, created = UserInfo.objects.get_or_create(user_id=obj.lensman_id, user_from=UserInfo.LENSMAN_USER, defaults=fields)
30 31
         if not created:
@@ -49,7 +50,7 @@ class LensmanIncomeExpensesInfoAdmin(admin.ModelAdmin):
49 50
 
50 51
 class UserInfoAdmin(admin.ModelAdmin):
51 52
     readonly_fields = ('user_id', )
52
-    list_display = ('user_id', 'user_from', 'username', 'wx_uid', 'name', 'sex', 'nickname', 'phone', 'location', 'balance', 'user_status', 'status', 'created_at', 'updated_at')
53
+    list_display = ('user_id', 'user_from', 'username', 'wx_uid', 'unionid', 'name', 'sex', 'nickname', 'phone', 'location', 'balance', 'user_status', 'status', 'created_at', 'updated_at')
53 54
     search_fields = ('name', 'phone', 'location')
54 55
     list_filter = ('user_from', 'sex', 'user_status', 'status')
55 56
 

+ 52 - 0
account/migrations/0013_auto_20160711_1436.py

@@ -0,0 +1,52 @@
1
+# -*- coding: utf-8 -*-
2
+from __future__ import unicode_literals
3
+
4
+from django.db import models, migrations
5
+import jsonfield.fields
6
+
7
+
8
+class Migration(migrations.Migration):
9
+
10
+    dependencies = [
11
+        ('account', '0012_auto_20160627_1419'),
12
+    ]
13
+
14
+    operations = [
15
+        migrations.CreateModel(
16
+            name='WechatInfo',
17
+            fields=[
18
+                ('id', models.AutoField(verbose_name='ID', serialize=False, auto_created=True, primary_key=True)),
19
+                ('status', models.BooleanField(default=True, help_text='\u72b6\u6001', db_index=True, verbose_name='status')),
20
+                ('created_at', models.DateTimeField(help_text='\u521b\u5efa\u65f6\u95f4', verbose_name='created_at', auto_now_add=True)),
21
+                ('updated_at', models.DateTimeField(help_text='\u66f4\u65b0\u65f6\u95f4', verbose_name='updated_at', auto_now=True)),
22
+                ('unionid', models.CharField(help_text='\u5fae\u4fe1 Union ID', max_length=255, null=True, verbose_name='unionid', blank=True)),
23
+                ('openids', jsonfield.fields.JSONField(help_text='\u5fae\u4fe1 Open IDs', null=True, verbose_name='openids', blank=True)),
24
+                ('sex', models.IntegerField(default=1, help_text='\u7528\u6237\u6027\u522b', verbose_name='sex', choices=[(1, '\u7537'), (0, '\u5973')])),
25
+                ('nickname', models.CharField(help_text='\u7528\u6237\u6635\u79f0', max_length=255, null=True, verbose_name='nickname', blank=True)),
26
+                ('headimgurl', models.CharField(help_text='\u7528\u6237\u5934\u50cf', max_length=255, null=True, verbose_name='headimgurl', blank=True)),
27
+                ('country', models.CharField(help_text='\u7528\u6237\u56fd\u5bb6', max_length=255, null=True, verbose_name='country', blank=True)),
28
+                ('province', models.CharField(help_text='\u7528\u6237\u7701\u4efd', max_length=255, null=True, verbose_name='province', blank=True)),
29
+                ('city', models.CharField(help_text='\u7528\u6237\u57ce\u5e02', max_length=255, null=True, verbose_name='city', blank=True)),
30
+                ('location', models.CharField(help_text='\u7528\u6237\u5730\u5740', max_length=255, null=True, verbose_name='location', blank=True)),
31
+            ],
32
+            options={
33
+                'verbose_name': 'wechatinfo',
34
+                'verbose_name_plural': 'wechatinfo',
35
+            },
36
+        ),
37
+        migrations.AddField(
38
+            model_name='lensmaninfo',
39
+            name='unionid',
40
+            field=models.CharField(null=True, max_length=255, blank=True, help_text='\u5fae\u4fe1 Union ID', unique=True, verbose_name='unionid', db_index=True),
41
+        ),
42
+        migrations.AddField(
43
+            model_name='lensmaninfo',
44
+            name='user_status',
45
+            field=models.IntegerField(default=0, verbose_name='user_status', choices=[(0, '\u672a\u9a8c\u8bc1'), (1, '\u5df2\u6fc0\u6d3b'), (2, '\u5df2\u7981\u7528'), (3, '\u5df2\u5220\u9664'), (10, '\u5df2\u5206\u914d')]),
46
+        ),
47
+        migrations.AlterField(
48
+            model_name='userinfo',
49
+            name='unionid',
50
+            field=models.CharField(null=True, max_length=255, blank=True, help_text='\u5fae\u4fe1 Union ID', unique=True, verbose_name='unionid', db_index=True),
51
+        ),
52
+    ]

+ 56 - 2
account/models.py

@@ -2,6 +2,7 @@
2 2
 
3 3
 from django.db import models
4 4
 from django.utils.translation import ugettext_lazy as _
5
+from jsonfield import JSONField
5 6
 
6 7
 from pai2.basemodels import CreateUpdateMixin
7 8
 
@@ -15,8 +16,24 @@ class LensmanInfo(CreateUpdateMixin):
15 16
         (FEMALE, u'女'),
16 17
     )
17 18
 
19
+    UNVERIFIED = 0
20
+    ACTIVATED = 1
21
+    DISABLED = 2
22
+    DELETED = 3
23
+    ASSIGN = 10
24
+
25
+    USER_STATUS = (
26
+        (UNVERIFIED, u'未验证'),
27
+        (ACTIVATED, u'已激活'),
28
+        (DISABLED, u'已禁用'),
29
+        (DELETED, u'已删除'),
30
+        (ASSIGN, u'已分配'),
31
+    )
32
+
18 33
     lensman_id = models.CharField(_(u'lensman_id'), max_length=255, blank=True, null=True, help_text=u'摄影师唯一标识', db_index=True, unique=True)
19 34
 
35
+    unionid = models.CharField(_(u'unionid'), max_length=255, blank=True, null=True, help_text=u'微信 Union ID', db_index=True, unique=True)
36
+
20 37
     username = models.CharField(_(u'username'), max_length=255, blank=True, null=True, help_text=u'摄影师用户名', db_index=True, unique=True)
21 38
     password = models.CharField(_(u'password'), max_length=255, blank=True, null=True, help_text=u'摄影师密码')
22 39
     encryption = models.CharField(_(u'encryption'), max_length=255, blank=True, null=True, help_text=u'摄影师密码')
@@ -30,6 +47,8 @@ class LensmanInfo(CreateUpdateMixin):
30 47
 
31 48
     balance = models.IntegerField(_(u'balance'), default=0, help_text=u'摄影师余额(分)')
32 49
 
50
+    user_status = models.IntegerField(_(u'user_status'), choices=USER_STATUS, default=UNVERIFIED)
51
+
33 52
     signup_ip = models.CharField(_(u'signup_ip'), max_length=255, blank=True, null=True, help_text=_(u'注册IP'))
34 53
     login_ip = models.CharField(_(u'login_ip'), max_length=255, blank=True, null=True, help_text=_(u'登录IP'))
35 54
     login_at = models.DateTimeField(_(u'login_at'), blank=True, null=True, help_text=_(u'登录时间'))
@@ -41,6 +60,15 @@ class LensmanInfo(CreateUpdateMixin):
41 60
     def __unicode__(self):
42 61
         return unicode(self.pk)
43 62
 
63
+    @property
64
+    def data(self):
65
+        return {
66
+            'name': self.name,
67
+            'sex': self.sex,
68
+            'phone': self.phone,
69
+            'location': self.location,
70
+        }
71
+
44 72
 
45 73
 class LensmanLoginLogInfo(CreateUpdateMixin):
46 74
     SUCCESS = 0
@@ -91,6 +119,33 @@ class LensmanIncomeExpensesInfo(CreateUpdateMixin):
91 119
         return unicode(self.pk)
92 120
 
93 121
 
122
+class WechatInfo(CreateUpdateMixin):
123
+    MALE = 1
124
+    FEMALE = 0
125
+
126
+    SEX_TYPE = (
127
+        (MALE, u'男'),
128
+        (FEMALE, u'女'),
129
+    )
130
+
131
+    unionid = models.CharField(_(u'unionid'), max_length=255, blank=True, null=True, help_text=u'微信 Union ID')
132
+    openids = JSONField(_(u'openids'), blank=True, null=True, help_text=u'微信 Open IDs')
133
+    sex = models.IntegerField(_(u'sex'), choices=SEX_TYPE, default=MALE, help_text=u'用户性别')
134
+    nickname = models.CharField(_(u'nickname'), max_length=255, blank=True, null=True, help_text=u'用户昵称')
135
+    headimgurl = models.CharField(_(u'headimgurl'), max_length=255, blank=True, null=True, help_text=u'用户头像')
136
+    country = models.CharField(_(u'country'), max_length=255, blank=True, null=True, help_text=u'用户国家')
137
+    province = models.CharField(_(u'province'), max_length=255, blank=True, null=True, help_text=u'用户省份')
138
+    city = models.CharField(_(u'city'), max_length=255, blank=True, null=True, help_text=u'用户城市')
139
+    location = models.CharField(_(u'location'), max_length=255, blank=True, null=True, help_text=u'用户地址')
140
+
141
+    class Meta:
142
+        verbose_name = _(u'wechatinfo')
143
+        verbose_name_plural = _(u'wechatinfo')
144
+
145
+    def __unicode__(self):
146
+        return unicode(self.pk)
147
+
148
+
94 149
 class UserInfo(CreateUpdateMixin):
95 150
     APP_USER = 0
96 151
     WX_USER = 1
@@ -135,8 +190,7 @@ class UserInfo(CreateUpdateMixin):
135 190
     password = models.CharField(_(u'password'), max_length=255, blank=True, null=True, help_text=u'用户密码')
136 191
     # 微信授权用户
137 192
     wx_uid = models.CharField(_(u'wx_uid'), max_length=255, blank=True, null=True, help_text=u'微信唯一标识', db_index=True, unique=True)
138
-    unionid = models.CharField(_(u'unionid'), max_length=255, blank=True, null=True, help_text=u'微信 Union ID')
139
-    # openid = models.CharField(_(u'openid'), max_length=255, blank=True, null=True, help_text=u'微信 Open ID')
193
+    unionid = models.CharField(_(u'unionid'), max_length=255, blank=True, null=True, help_text=u'微信 Union ID', db_index=True, unique=True)
140 194
     # 用户基本信息
141 195
     name = models.CharField(_(u'name'), max_length=255, blank=True, null=True, help_text=u'用户姓名')
142 196
     sex = models.IntegerField(_(u'sex'), choices=SEX_TYPE, default=MALE, help_text=u'用户性别')

+ 4 - 4
account/views.py

@@ -130,8 +130,8 @@ def user_login_api(request):
130 130
 
131 131
 def wx_authorize_api(request):
132 132
     user_id = request.POST.get('user_id', '')
133
-    wx_uid = request.POST.get('wx_uid', '')
134 133
 
134
+    openid = wx_uid = request.POST.get('wx_uid', '')
135 135
     unionid = request.POST.get('unionid', '')
136 136
 
137 137
     sex = request.POST.get('sex', 0)
@@ -141,9 +141,9 @@ def wx_authorize_api(request):
141 141
     province = request.POST.get('province', '')
142 142
     city = request.POST.get('city', '')
143 143
 
144
-    # 判断 wx_uid 是否已经存在,如果已经存在,则直接返回改帐户信息
144
+    # 判断 unionid 是否已经存在,如果已经存在,则直接返回改帐户信息
145 145
     try:
146
-        user = UserInfo.objects.get(wx_uid=wx_uid)
146
+        user = UserInfo.objects.get(unionid=unionid)
147 147
     except UserInfo.DoesNotExist:
148 148
         user = None
149 149
 
@@ -163,7 +163,7 @@ def wx_authorize_api(request):
163 163
             'data': user.data,
164 164
         })
165 165
 
166
-    # wx_uid 不存在
166
+    # unionid 不存在
167 167
     # 判断 user_id 是否存在并且为分配用户,如果存在并且为分配用户,则直接在该帐户上更新,否则则直接创建帐户
168 168
 
169 169
     signup_ip, signup_at = ip_addr(request), tc.utc_datetime()

+ 8 - 1
api/urls.py

@@ -27,6 +27,7 @@ urlpatterns = [
27 27
 
28 28
 # 摄影师相关
29 29
 urlpatterns += [
30
+    url(r'^l/submit$', lensman_views.lensman_submit_api, name='lensman_submit_api'),  # 摄影师登录
30 31
     url(r'^l/login$', lensman_views.lensman_login_api, name='lensman_login_api'),  # 摄影师登录
31 32
     url(r'^l/photos/upload$', lensman_views.lensman_upload_photo_api, name='lensman_upload_photo_api'),  # 摄影师上传照片
32 33
 ]
@@ -104,7 +105,13 @@ urlpatterns += [
104 105
     url(r'^wx/balance_withdraw$', pay_views.wx_balance_withdraw_api, name='wx_balance_withdraw_api'),  # 余额提现: 企业付款/现金红包
105 106
 ]
106 107
 
107
-# 分享相关
108
+# 微信授权相关
109
+urlpatterns += [
110
+    url(r'^get_openid$', wechat_views.get_openid, name='get_openid'),
111
+    url(r'^to_redirect$', wechat_views.to_redirect, name='to_redirect'),
112
+]
113
+
114
+# 微信分享相关
108 115
 urlpatterns += [
109 116
     url(r'^wx/jsapi_signature$', wechat_views.wx_jsapi_signature_api, name='wx_jsapi_signature_api'),  # jsapi_signature
110 117
 ]

+ 29 - 0
group/lensman_views.py

@@ -26,6 +26,35 @@ from utils.watermark_utils import watermark_wrap
26 26
 r = settings.REDIS_CACHE
27 27
 
28 28
 
29
+def lensman_submit_api(request):
30
+    """
31
+    摄影师信息提交
32
+    :param request:
33
+    :return:
34
+    """
35
+    unionid = request.POST.get('unionid', '')
36
+    phone = request.POST.get('phone', '')
37
+
38
+    if LensmanInfo.objects.filter(phone=phone).exclude(unionid=unionid).exists():
39
+        return response(LensmanStatusCode.LENSMAN_PHONE_ALREADY_EXISTS)
40
+
41
+    fields = {
42
+        'name': request.POST.get('name', ''),
43
+        'sex': int(request.POST.get('sex', 1)),
44
+        'phone': phone,
45
+        'location': request.POST.get('location', ''),
46
+        'user_status': LensmanInfo.UNVERIFIED,
47
+    }
48
+
49
+    lensman, created = LensmanInfo.objects.get_or_create(unionid=unionid, defaults=fields)
50
+    if not created:
51
+        for key, value in fields.iteritems():
52
+            setattr(lensman, key, value)
53
+        lensman.save()
54
+
55
+    return response(200, 'Submit Success', u'提交成功', {})
56
+
57
+
29 58
 def lensman_login_api(request):
30 59
     """
31 60
     摄影师登录

+ 154 - 0
page/templates/page/lensman_oauth.html

@@ -0,0 +1,154 @@
1
+{% load staticfiles %}
2
+
3
+<!DOCTYPE html>
4
+<html lang="zh-CN">
5
+<head>
6
+    <meta charset="utf-8">
7
+    <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
8
+    <meta name="format-detection" content="telephone=no,email=no,address=no">
9
+    <meta name="viewport" content="width=device-width,initial-scale=1.0,user-scalable=no">
10
+    <title>摄影师授权</title>
11
+
12
+    <link href="https://res.wx.qq.com/open/libs/weui/0.4.3/weui.min.css" rel="stylesheet" type="text/css" />
13
+
14
+    <style>
15
+        input:required:invalid {
16
+            color: #E64340;
17
+        }
18
+        input:required:valid {
19
+            color: rgba(0, 0, 0);
20
+        }
21
+
22
+    </style>
23
+</head>
24
+<body>
25
+    <div class="container" >
26
+        <div class="weui_cells weui_cells_form">
27
+            <div class="weui_cell">
28
+                <div class="weui_cell_hd"><label for="" class="weui_label">姓名</label></div>
29
+                <div class="weui_cell_bd weui_cell_primary">
30
+                    <input id="name" class="weui_input" type="text" value="{{ lensman_info.name }}" placeholder="请输入姓名">
31
+                </div>
32
+            </div>
33
+            <div class="weui_cell weui_cell_select weui_select_after">
34
+                <div class="weui_cell_hd"><label for="" class="weui_label">性别</label></div>
35
+                <div class="weui_cell_bd weui_cell_primary">
36
+                    <select id="sex" class="weui_select" name="select">
37
+                        <option value="1" {% ifequal lensman_info.sex 1 %}selected{% endifequal %}>男</option>
38
+                        <option value="0" {% ifequal lensman_info.sex 0 %}selected{% endifequal %}>女</option>
39
+                    </select>
40
+                </div>
41
+            </div>
42
+            <div class="weui_cell">
43
+                <div class="weui_cell_hd"><label for="" class="weui_label">手机号</label></div>
44
+                <div class="weui_cell_bd weui_cell_primary">
45
+                    <input id="phone" class="weui_input" type="text" required="required" pattern="[0-9]{11}" value="{{ lensman_info.phone }}" placeholder="请输入手机号">
46
+                </div>
47
+            </div>
48
+            <div class="weui_cell">
49
+                <div class="weui_cell_hd"><label for="" class="weui_label">地址</label></div>
50
+                <div class="weui_cell_bd weui_cell_primary">
51
+                    <input id="location" class="weui_input" type="text" value="{{ lensman_info.location }}" placeholder="请输入地址">
52
+                </div>
53
+            </div>
54
+        </div>
55
+
56
+        <br>
57
+
58
+        <button id="submit" class="weui_btn weui_btn_warn">确认</button>
59
+
60
+        <div class="weui_dialog_alert" id="dialog" style="display: none">
61
+            <div class="weui_mask"></div>
62
+            <div class="weui_dialog">
63
+                <div class="weui_dialog_hd"><strong id="title" class="weui_dialog_title">弹窗标题</strong></div>
64
+                <div id="content" class="weui_dialog_bd">弹窗内容,告知当前页面信息等</div>
65
+                <div class="weui_dialog_ft">
66
+                    <a href="javascript:;" class="weui_btn_dialog primary">确定</a>
67
+                </div>
68
+            </div>
69
+        </div>
70
+
71
+        <div id="toast" style="display: none;">
72
+            <div class="weui_mask_transparent"></div>
73
+            <div class="weui_toast">
74
+                <i class="weui_icon_toast"></i>
75
+                <p class="weui_toast_content">已完成</p>
76
+            </div>
77
+        </div>
78
+    </div>
79
+
80
+    <script src="//cdn.bootcss.com/zepto/1.1.6/zepto.min.js"></script>
81
+    <script>
82
+        $(function() {
83
+            function getURLParameter(name) {
84
+              return decodeURIComponent((new RegExp('[?|&]' + name + '=' + '([^&;]+?)(&|#|;|$)').exec(location.search) || [null, ''])[1].replace(/\+/g, '%20')) || null;
85
+            }
86
+
87
+            function show_error_dialog(title, content) {
88
+                $('#dialog #title').text(title);
89
+                $('#dialog #content').text(content);
90
+                $('#dialog').show();
91
+            }
92
+            
93
+            function data_check() {
94
+                var unionid = getURLParameter('unionid');
95
+                if (!unionid) {
96
+                    show_error_dialog('微信授权', '微信授权失败,请重新打开页面');
97
+                    return false;
98
+                }
99
+
100
+                var name = $('#name').val();
101
+                if (!name) {
102
+                    show_error_dialog('姓名', '姓名错误,请检查重新输入');
103
+                    return false;
104
+                }
105
+
106
+                var phone_valid = $('#phone').is(':valid');
107
+                if (!phone_valid) {
108
+                    show_error_dialog('手机号', '手机号错误,请检查重新输入');
109
+                    return false;
110
+                }
111
+
112
+                var location = $('#location').val();
113
+                if (!location) {
114
+                    show_error_dialog('地址', '地址错误,请检查重新输入');
115
+                    return false;
116
+                }
117
+
118
+                return {
119
+                    unionid: unionid,
120
+                    name: name,
121
+                    sex: $('#sex option:checked').val(),
122
+                    phone: $('#phone').val(),
123
+                    location: location,
124
+                }
125
+            }
126
+
127
+            $('#submit').click(function () {
128
+                var check_result = data_check();
129
+                if (check_result){
130
+                    $.ajax({
131
+                        type: 'POST',
132
+                        url: 'l/submit',
133
+                        data: check_result,
134
+                        success: function(data) {
135
+                            if (data.status == 200) {
136
+                                $('#toast').show();
137
+                                setTimeout(function () {
138
+                                    $('#toast').hide();
139
+                                }, 1000);
140
+                            } else {
141
+                                show_error_dialog('错误', data.description);
142
+                            }
143
+                        }
144
+                    })
145
+                }
146
+            });
147
+
148
+            $('#dialog .weui_btn_dialog').click(function () {
149
+                $('#dialog').hide();
150
+            })
151
+        });
152
+    </script>
153
+</body>
154
+</html>

+ 15 - 0
page/views.py

@@ -2,6 +2,8 @@
2 2
 
3 3
 from django.shortcuts import render
4 4
 
5
+from account.models import LensmanInfo
6
+
5 7
 
6 8
 def user_agreement(request):
7 9
     return render(request, 'page/user_agreement.html', {})
@@ -9,3 +11,16 @@ def user_agreement(request):
9 11
 
10 12
 def contact_us(request):
11 13
     return render(request, 'page/contact_us.html', {})
14
+
15
+
16
+def lensman_oauth(request):
17
+    unionid = request.GET.get('unionid', '')
18
+
19
+    try:
20
+        lensman = LensmanInfo.objects.get(unionid=unionid)
21
+    except LensmanInfo.DoesNotExist:
22
+        lensman = None
23
+
24
+    return render(request, 'page/lensman_oauth.html', {
25
+        'lensman_info': lensman and lensman.data
26
+    })

+ 8 - 0
pai2/urls.py

@@ -23,6 +23,7 @@ from rest_framework import routers
23 23
 
24 24
 from account import views as account_views
25 25
 from group import views as group_views
26
+from group import lensman_views
26 27
 from page import views as page_views
27 28
 from photo import views as photo_views
28 29
 from website import views as website_views
@@ -65,6 +66,8 @@ urlpatterns += [
65 66
 urlpatterns += [
66 67
     url(r'^page/user_agreement$', page_views.user_agreement, name='user_agreement'),  # 用户协议页面
67 68
     url(r'^page/contact_us$', page_views.contact_us, name='contact_us'),  # 联系我们页面
69
+
70
+    url(r'^page/lensman$', page_views.lensman_oauth, name='lensman_oauth'),  # 摄影师授权页面
68 71
 ]
69 72
 
70 73
 urlpatterns += [
@@ -75,6 +78,11 @@ urlpatterns += [
75 78
     url(r'^termofservice$', website_views.pai2_termofservice, name='pai2_termofservice'),  # 官网服务条款
76 79
 ]
77 80
 
81
+# 摄影师相关
82
+urlpatterns += [
83
+    url(r'^page/l/submit$', lensman_views.lensman_submit_api, name='lensman_submit_api'),  # 摄影师登录
84
+]
85
+
78 86
 # Wire up our API using automatic URL routing.
79 87
 # Additionally, we include login URLs for the browsable API.
80 88
 urlpatterns += [

+ 2 - 0
requirements.txt

@@ -11,12 +11,14 @@ django-logit==1.0.2
11 11
 django-multidomain==1.1.4
12 12
 django-shortuuidfield==0.1.3
13 13
 djangorestframework==3.3.1
14
+furl==0.4.95
14 15
 hiredis==0.2.0
15 16
 ipdb==0.8.1
16 17
 ipython==4.0.0
17 18
 jsonfield==1.0.3
18 19
 kkconst==1.1.2
19 20
 pep8==1.6.2
21
+pysnippets==1.0.2
20 22
 pytz==2015.7
21 23
 records==0.4.3
22 24
 redis==2.10.5

+ 2 - 0
utils/error/errno_utils.py

@@ -19,6 +19,8 @@ class LensmanStatusCode(BaseStatusCode):
19 19
     LENSMAN_NOT_FOUND = StatusCodeField(400001, u'Lensman Not Found', description=u'摄影师不存在')
20 20
     LENSMAN_PASSWORD_ERROR = StatusCodeField(400002, u'Lensman Password Error', description=u'摄影师密码错误')
21 21
 
22
+    LENSMAN_PHONE_ALREADY_EXISTS = StatusCodeField(400005, u'Lensman Phone Already Exists', description=u'手机号已经存在')
23
+
22 24
 
23 25
 class UserStatusCode(BaseStatusCode):
24 26
     """ 用户相关错误码  4001xx """

+ 33 - 0
wechat/views.py

@@ -1,10 +1,16 @@
1 1
 # -*- coding: utf-8 -*-
2 2
 
3 3
 import time
4
+import urllib
4 5
 
6
+import requests
5 7
 import shortuuid
8
+from CodeConvert import CodeConvert as cc
6 9
 from django.conf import settings
10
+from django.shortcuts import redirect
11
+from furl import furl
7 12
 from json_response import auto_response
13
+from pysnippets import dictsnippets as dsnippets
8 14
 from wechatpy import WeChatClient
9 15
 
10 16
 
@@ -13,6 +19,33 @@ WECHAT = settings.WECHAT
13 19
 JSAPI = WECHAT.get('JSAPI', {})
14 20
 
15 21
 
22
+def get_openid(request):
23
+    scope = request.GET.get('scope', 'snsapi_userinfo')
24
+    redirect_url = request.GET.get('redirect_url', '')
25
+    default_url = request.GET.get('default_url', '')
26
+
27
+    if request.weixin:
28
+        authorize_url = settings.WECHAT_GET_CODE_USERINFO if scope == 'snsapi_userinfo' else settings.WECHAT_GET_CODE_BASE
29
+        get_code_url = authorize_url % (JSAPI['appID'], urllib.quote_plus(settings.WECHAT_REDIRECT_URI), urllib.quote_plus(redirect_url))
30
+        return redirect(get_code_url)
31
+
32
+    return redirect(default_url if default_url else redirect_url)
33
+
34
+
35
+def to_redirect(request):
36
+    code = request.GET.get('code', '')
37
+    state = request.GET.get('state', '')
38
+
39
+    access_info = requests.get(settings.WECHAT_GET_OAUTH2_ACCESS_TOKEN % (JSAPI['appID'], JSAPI['appsecret'], code), verify=False).json()
40
+    unionid, openid, access_token = access_info.get('unionid', ''), access_info.get('openid', ''), access_info.get('access_token', '')
41
+
42
+    res = requests.get(settings.WECHAT_GET_USERINFO % (access_token, openid), verify=False)
43
+    res.encoding = 'utf-8'
44
+    userinfo = res.json()
45
+
46
+    return redirect(furl(state).add(cc.Convert2Utf8(dsnippets.filter(userinfo, ['unionid', 'openid', 'nickname', 'headimgurl']))).url)
47
+
48
+
16 49
 @auto_response
17 50
 def wx_jsapi_signature_api(request):
18 51
     url = request.GET.get('url', '')