• <label id="pxtpz"><meter id="pxtpz"></meter></label>
      1. <span id="pxtpz"><optgroup id="pxtpz"></optgroup></span>

        當(dāng)前位置:雨林木風(fēng)下載站 > 網(wǎng)絡(luò)軟件教程 > 詳細(xì)頁(yè)面

        來(lái)看看你的顏值多高吧!基于Python開發(fā)的公眾號(hào)

        來(lái)看看你的顏值多高吧!基于Python開發(fā)的公眾號(hào)

        更新時(shí)間:2025-09-20 文章作者:未知 信息來(lái)源:網(wǎng)絡(luò) 閱讀次數(shù):

        導(dǎo)微信(WeChat)是騰訊公司于2011年1月21日推出的一個(gè)為智能終端提供即時(shí)通訊服務(wù)的免費(fèi)應(yīng)用程序,由張小龍所帶領(lǐng)的騰訊廣州研發(fā)中心產(chǎn)品團(tuán)隊(duì)打造 [2] 。微信支持跨通信運(yùn)營(yíng)商、跨操作系統(tǒng)平臺(tái)...
        微信(WeChat)是騰訊公司于2011年1月21日推出的一個(gè)為智能終端提供即時(shí)通訊服務(wù)的免費(fèi)應(yīng)用程序,由張小龍所帶領(lǐng)的騰訊廣州研發(fā)中心產(chǎn)品團(tuán)隊(duì)打造 [2] 。微信支持跨通信運(yùn)營(yíng)商、跨操作系統(tǒng)平臺(tái)通過(guò)網(wǎng)絡(luò)快速發(fā)送免費(fèi)(需消耗少量網(wǎng)絡(luò)流量)語(yǔ)音短信、視頻、圖片和文字,同時(shí),也可以使用通過(guò)共享流媒體內(nèi)容的資料和基于位置的社交插件“搖一搖”、“漂流瓶”、“朋友圈”、”公眾平臺(tái)“、”語(yǔ)音記事本“等服務(wù)插件。
        這是一個(gè)基于Python的微信公眾號(hào)開發(fā)之顏值檢測(cè),今天我們把用戶的圖片通過(guò)騰訊的AI平臺(tái)分析后再返回給用戶。來(lái)一起體驗(yàn)下公眾號(hào)的顏值檢測(cè)吧

        效果圖

        1691280-3107ca5c3aec2f5b.png

        1691280-201fade473e79cc3.jpg

        1691280-cc338ba77cc79eaf.jpg

        一. 接入騰訊AI平臺(tái)

        我們先看一下官方人臉檢測(cè)與分析接口的描述:

        檢測(cè)給定圖片(Image)中的所有人臉(Face)的位置和相應(yīng)的面部屬性。位置包括(x, y, w, h),面部屬性包括性別(gender), 年齡(age), 表情(expression), 魅力(beauty), 眼鏡(glass)和姿態(tài)(pitch,roll,yaw)。

        請(qǐng)求參數(shù)包括下面幾個(gè):

        • app_id 應(yīng)用標(biāo)識(shí),我們?cè)贏I平臺(tái)注冊(cè)后就可以得到app_id

        • time_stamp 時(shí)間戳

        • nonce_str 隨機(jī)字符串

        • sign 簽名信息,需要我們自己去計(jì)算

        • image 需要檢測(cè)的圖片(上限1M)

        • mode 檢測(cè)模式

        1.接口鑒權(quán),構(gòu)造請(qǐng)求參數(shù)

        官方給了我們接口鑒權(quán)的計(jì)算方法。

        1. 將<key, value>請(qǐng)求參數(shù)對(duì)按key進(jìn)行字典升序排序,得到有序的參數(shù)對(duì)列表N

        2. 將列表N中的參數(shù)對(duì)按URL鍵值對(duì)的格式拼接成字符串,得到字符串T(如:key1=value1&key2=value2),URL鍵值拼接過(guò)程value部分需要URL編碼,URL編碼算法用大寫字母,例如%E8,而不是小寫%e8

        3. 將應(yīng)用密鑰以app_key為鍵名,組成URL鍵值拼接到字符串T末尾,得到字符串S(如:key1=value1&key2=value2&app_key=密鑰)

        4. 對(duì)字符串S進(jìn)行MD5運(yùn)算,將得到的MD5值所有字符轉(zhuǎn)換成大寫,得到接口請(qǐng)求簽名

        2.請(qǐng)求接口地址

        請(qǐng)求接口信息,我們用 requests 發(fā)送請(qǐng)求,會(huì)得到返回的 json 格式的圖像信息pip install requests安裝requests。

        3.處理返回的信息

        處理返回的信息,把信息展示在圖片上,再把處理后的圖片保存。這里我們用到 opencv ,和 pillow 兩個(gè)庫(kù)pip install pillowpip install opencv-python來(lái)安裝。

        開始編寫代碼,我們新建一個(gè)face_id.py 文件來(lái)對(duì)接AI平臺(tái),并且返回檢測(cè)后的圖像數(shù)據(jù)。

        import time
        import random
        import base64
        import hashlib
        import requests
        from urllib.parse import urlencode
        import cv2
        import numpy as np
        from PIL import Image, ImageDraw, ImageFont
        import os
        
        
        # 一.計(jì)算接口鑒權(quán),構(gòu)造請(qǐng)求參數(shù)
        
        def random_str():
            '''得到隨機(jī)字符串nonce_str'''
            str = 'abcdefghijklmnopqrstuvwxyz'
            r = ''
            for i in range(15):
                index = random.randint(0,25)
                r += str[index]
            return r
        
        
        def image(name):
            with open(name, 'rb') as f:
                content = f.read()
            return base64.b64encode(content)
        
        
        def get_params(img):
            '''組織接口請(qǐng)求的參數(shù)形式,并且計(jì)算sign接口鑒權(quán)信息,
            最終返回接口請(qǐng)求所需要的參數(shù)字典'''
            params = {
                'app_id': '1106860829',
                'time_stamp': str(int(time.time())),
                'nonce_str': random_str(),
                'image': img,
                'mode': '0'
        
            }
        
            sort_dict = sorted(params.items(), key=lambda item: item[0], reverse=False)  # 排序
            sort_dict.append(('app_key', 'P8Gt8nxi6k8vLKbS'))  # 添加app_key
            rawtext = urlencode(sort_dict).encode()  # URL編碼
            sha = hashlib.md5()
            sha.update(rawtext)
            md5text = sha.hexdigest().upper()  # 計(jì)算出sign,接口鑒權(quán)
            params['sign'] = md5text  # 添加到請(qǐng)求參數(shù)列表中
            return params
        
        # 二.請(qǐng)求接口URL
        
        
        def access_api(img):
            frame = cv2.imread(img)
            nparry_encode = cv2.imencode('.jpg', frame)[1]
            data_encode = np.array(nparry_encode)
            img_encode = base64.b64encode(data_encode)  # 圖片轉(zhuǎn)為base64編碼格式
            url = 'https://api.ai.qq.com/fcgi-bin/face/face_detectface'
            res = requests.post(url, get_params(img_encode)).json()  # 請(qǐng)求URL,得到j(luò)son信息
            # 把信息顯示到圖片上
            if res['ret'] == 0:  # 0代表請(qǐng)求成功
                pil_img = Image.fromarray(cv2.cvtColor(frame, cv2.COLOR_BGR2RGB))  # 把opencv格式轉(zhuǎn)換為PIL格式,方便寫漢字
                draw = ImageDraw.Draw(pil_img)
                for obj in res['data']['face_list']:
                    img_width = res['data']['image_width']  # 圖像寬度
                    img_height = res['data']['image_height']  # 圖像高度
                    # print(obj)
                    x = obj['x']  # 人臉框左上角x坐標(biāo)
                    y = obj['y']  # 人臉框左上角y坐標(biāo)
                    w = obj['width']  # 人臉框?qū)挾?            h = obj['height']  # 人臉框高度
                    # 根據(jù)返回的值,自定義一下顯示的文字內(nèi)容
                    if obj['glass'] == 1:  # 眼鏡
                        glass = '有'
                    else:
                        glass = '無(wú)'
                    if obj['gender'] >= 70:  # 性別值從0-100表示從女性到男性
                        gender = '男'
                    elif 50 <= obj['gender'] < 70:
                        gender = "娘"
                    elif obj['gender'] < 30:
                        gender = '女'
                    else:
                        gender = '女漢子'
                    if 90 < obj['expression'] <= 100:  # 表情從0-100,表示笑的程度
                        expression = '一笑傾城'
                    elif 80 < obj['expression'] <= 90:
                        expression = '心花怒放'
                    elif 70 < obj['expression'] <= 80:
                        expression = '興高采烈'
                    elif 60 < obj['expression'] <= 70:
                        expression = '眉開眼笑'
                    elif 50 < obj['expression'] <= 60:
                        expression = '喜上眉梢'
                    elif 40 < obj['expression'] <= 50:
                        expression = '喜氣洋洋'
                    elif 30 < obj['expression'] <= 40:
                        expression = '笑逐顏開'
                    elif 20 < obj['expression'] <= 30:
                        expression = '似笑非笑'
                    elif 10 < obj['expression'] <= 20:
                        expression = '半嗔半喜'
                    elif 0 <= obj['expression'] <= 10:
                        expression = '黯然傷神'
                    delt = h // 5  # 確定文字垂直距離
                    # 寫入圖片
                    if len(res['data']['face_list']) > 1:  # 檢測(cè)到多個(gè)人臉,就把信息寫入人臉框內(nèi)
                        font = ImageFont.truetype('yahei.ttf', w // 8, encoding='utf-8')  # 提前把字體文件下載好
                        draw.text((x + 10, y + 10), '性別 :' + gender, (76, 176, 80), font=font)
                        draw.text((x + 10, y + 10 + delt * 1), '年齡 :' + str(obj['age']), (76, 176, 80), font=font)
                        draw.text((x + 10, y + 10 + delt * 2), '表情 :' + expression, (76, 176, 80), font=font)
                        draw.text((x + 10, y + 10 + delt * 3), '魅力 :' + str(obj['beauty']), (76, 176, 80), font=font)
                        draw.text((x + 10, y + 10 + delt * 4), '眼鏡 :' + glass, (76, 176, 80), font=font)
                    elif img_width - x - w < 170:  # 避免圖片太窄,導(dǎo)致文字顯示不完全
                        font = ImageFont.truetype('yahei.ttf', w // 8, encoding='utf-8')
                        draw.text((x + 10, y + 10), '性別 :' + gender, (76, 176, 80), font=font)
                        draw.text((x + 10, y + 10 + delt * 1), '年齡 :' + str(obj['age']), (76, 176, 80), font=font)
                        draw.text((x + 10, y + 10 + delt * 2), '表情 :' + expression, (76, 176, 80), font=font)
                        draw.text((x + 10, y + 10 + delt * 3), '魅力 :' + str(obj['beauty']), (76, 176, 80), font=font)
                        draw.text((x + 10, y + 10 + delt * 4), '眼鏡 :' + glass, (76, 176, 80), font=font)
                    else:
                        font = ImageFont.truetype('yahei.ttf', 20, encoding='utf-8')
                        draw.text((x + w + 10, y + 10), '性別 :' + gender, (76, 176, 80), font=font)
                        draw.text((x + w + 10, y + 10 + delt * 1), '年齡 :' + str(obj['age']), (76, 176, 80), font=font)
                        draw.text((x + w + 10, y + 10 + delt * 2), '表情 :' + expression, (76, 176, 80), font=font)
                        draw.text((x + w + 10, y + 10 + delt * 3), '魅力 :' + str(obj['beauty']), (76, 176, 80), font=font)
                        draw.text((x + w + 10, y + 10 + delt * 4), '眼鏡 :' + glass, (76, 176, 80), font=font)
        
                    draw.rectangle((x, y, x + w, y + h), outline="#4CB050")  # 畫出人臉?lè)娇?            cv2img = cv2.cvtColor(np.array(pil_img), cv2.COLOR_RGB2BGR)  # 把 pil 格式轉(zhuǎn)換為 cv
                    cv2.imwrite('faces/{}'.format(os.path.basename(img)), cv2img)  # 保存圖片到 face 文件夾下
                    return '檢測(cè)成功'
            else:
                return '檢測(cè)失敗'

        到這里我們的人臉檢測(cè)接口接入及圖片處理就完成了。之后在收到用戶發(fā)送的圖片信息后,調(diào)用這個(gè)函數(shù),把處理后的圖片返回給用戶就可以。

        返回圖片給用戶

        當(dāng)收到用戶圖片時(shí),需要以下幾個(gè)步驟:

        保存圖片

        當(dāng)接收到用戶圖片后,我們要先把圖片保存起來(lái),之后才能去調(diào)用人臉?lè)治鼋涌冢褕D片信息傳遞過(guò)去,我們需要編寫一個(gè) img_download 函數(shù)來(lái)下載圖片。詳見(jiàn)下方代碼

        調(diào)用人臉?lè)治鼋涌?/h3>

        圖片下載后,調(diào)用 face_id.py 文件里的接口函數(shù),得到處理后的圖片。

        上傳圖片

        檢測(cè)結(jié)果是一張新的圖片,要把圖片發(fā)送給用戶我們需要一個(gè) Media_ID,要獲取Media_ID必須先把圖片上傳為臨時(shí)素材,所以這里我們需要一個(gè)img_upload函數(shù)來(lái)上傳圖片,并且在上傳時(shí)需要用到一個(gè)access_token,我們通過(guò)一個(gè)函數(shù)來(lái)獲取. 獲取access_token必須要把我們自己的IP地址加入白名單,否則是獲取不到的。請(qǐng)登錄“微信公眾平臺(tái)-開發(fā)-基本配置”提前將服務(wù)器IP地址添加到IP白名單中,可以在http://ip.qq.com/查看本機(jī)的IP...

        開始編寫代碼,我們新建一個(gè) utils.py 來(lái)下載、上傳圖片

        import requests
        import json
        import threading
        import time
        import os
        
        token = ''
        app_id = 'wxfc6adcdd7593a712'
        secret = '429d85da0244792be19e0deb29615128'
        
        
        def img_download(url, name):
            r = requests.get(url)
            with open('images/{}-{}.jpg'.format(name, time.strftime("%Y_%m_%d%H_%M_%S", time.localtime())), 'wb') as fd:
                fd.write(r.content)
            if os.path.getsize(fd.name) >= 1048576:
                return 'large'
            # print('namename', os.path.basename(fd.name))
            return os.path.basename(fd.name)
        
        
        def get_access_token(appid, secret):
            '''獲取access_token,100分鐘刷新一次'''
        
            url = 'https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid={}&secret={}'.format(appid, secret)
            r = requests.get(url)
            parse_json = json.loads(r.text)
            global token
            token = parse_json['access_token']
            global timer
            timer = threading.Timer(6000, get_access_token)
            timer.start()
        
        
        def img_upload(mediaType, name):
            global token
            url = "https://api.weixin.qq.com/cgi-bin/media/upload?access_token=%s&type=%s" % (token, mediaType)
            files = {'media': open('{}'.format(name), 'rb')}
            r = requests.post(url, files=files)
            parse_json = json.loads(r.text)
            return parse_json['media_id']
        
        get_access_token(app_id, secret)

        返回給用戶

        我們簡(jiǎn)單修改下收到圖片后的邏輯,收到圖片后經(jīng)過(guò)人臉檢測(cè),上傳獲得Media_ID,我們要做的就是把圖片返回給用戶即可。直接看connect.py的代碼

        import falcon
        from falcon import uri
        from wechatpy.utils import check_signature
        from wechatpy.exceptions import InvalidSignatureException
        from wechatpy import parse_message
        from wechatpy.replies import TextReply, ImageReply
        
        from utils import img_download, img_upload
        from face_id import access_api
        
        
        class Connect(object):
        
            def on_get(self, req, resp):
                query_string = req.query_string
                query_list = query_string.split('&')
                b = {}
                for i in query_list:
                    b[i.split('=')[0]] = i.split('=')[1]
        
                try:
                    check_signature(token='lengxiao', signature=b['signature'], timestamp=b['timestamp'], nonce=b['nonce'])
                    resp.body = (b['echostr'])
                except InvalidSignatureException:
                    pass
                resp.status = falcon.HTTP_200
        
            def on_post(self, req, resp):
                xml = req.stream.read()
                msg = parse_message(xml)
                if msg.type == 'text':
                    reply = TextReply(content=msg.content, message=msg)
                    xml = reply.render()
                    resp.body = (xml)
                    resp.status = falcon.HTTP_200
                elif msg.type == 'image':
                    name = img_download(msg.image, msg.source)  # 下載圖片
                    r = access_api('images/' + name)
                    if r == '檢測(cè)成功':
                        media_id = img_upload('image', 'faces/' + name)  # 上傳圖片,得到 media_id
                        reply = ImageReply(media_id=media_id, message=msg)
                    else:
                        reply = TextReply(content='人臉檢測(cè)失敗,請(qǐng)上傳1M以下人臉清晰的照片', message=msg)
                    xml = reply.render()
                    resp.body = (xml)
                    resp.status = falcon.HTTP_200
        
        app = falcon.API()
        connect = Connect()
        app.add_route('/connect', connect)

        至此我們的工作就做完了,我們的公眾號(hào)可以進(jìn)行顏值檢測(cè)了。本來(lái)我打算用在自己公眾號(hào)上的,但是還存在下面幾個(gè)問(wèn)題,所以沒(méi)有使用。

        1. 微信的機(jī)制,我們的程序必須在5s內(nèi)給出響應(yīng)。不然就會(huì)報(bào)'公眾號(hào)提供的服務(wù)出現(xiàn)故障'。然而處理圖片有時(shí)會(huì)比較慢,經(jīng)常會(huì)超過(guò)5s。所以正確的處理方式應(yīng)該是拿到用戶的請(qǐng)求后立即返回一個(gè)空字符串表示我們收到了,之后單獨(dú)創(chuàng)建一個(gè)線程去處理圖片,當(dāng)圖片處理完后通過(guò)客服接口發(fā)送給用戶。可惜的是未認(rèn)證的公眾號(hào)沒(méi)有客服接口,所以沒(méi)辦法,超過(guò)5s就會(huì)報(bào)錯(cuò)。

        2. 無(wú)法自定義菜單,一旦啟用了自定義開發(fā),菜單也需要自定義配置,但是未認(rèn)證的公眾號(hào)沒(méi)有權(quán)限通過(guò)程序來(lái)配置菜單,只能在微信后臺(tái)配置。

        所以,我并沒(méi)有在我的公眾號(hào)上啟用這個(gè)程序,但是如果有認(rèn)證的公眾號(hào),可以嘗試開發(fā)各種好玩的功能。

        相關(guān)推薦:

        微信公眾平臺(tái)開發(fā)一鍵關(guān)注微信公眾平臺(tái)賬號(hào)

        微信公眾平臺(tái)開發(fā)嘗試,微信公眾平臺(tái)

        視頻:傳智、黑馬微信公眾平臺(tái)開發(fā)視頻教程

        以上就是來(lái)看看你的顏值多高吧!基于Python開發(fā)的公眾號(hào)的詳細(xì)內(nèi)容,更多請(qǐng)關(guān)注php中文網(wǎng)其它相關(guān)文章!


        微信提供公眾平臺(tái)、朋友圈、消息推送等功能,用戶可以通過(guò)“搖一搖”、“搜索號(hào)碼”、“附近的人”、掃二維碼方式添加好友和關(guān)注公眾平臺(tái),同時(shí)微信將內(nèi)容分享給好友以及將用戶看到的精彩內(nèi)容分享到微信朋友圈。

        溫馨提示:喜歡本站的話,請(qǐng)收藏一下本站!

        本類教程下載

        系統(tǒng)下載排行

        主站蜘蛛池模板: 亚洲色大成网站www尤物| 亚洲大香人伊一本线| 最新亚洲人成网站在线观看| 九九精品免费视频| 羞羞网站免费观看| 99精品免费观看| 亚洲天天做日日做天天看| 久久er国产精品免费观看2| 亚洲精品国产精品乱码在线观看| 亚洲三级中文字幕| 国产精品福利片免费看| 亚洲日韩涩涩成人午夜私人影院| 日亚毛片免费乱码不卡一区| 亚洲国产成人精品久久久国产成人一区二区三区综 | 亚洲三级视频在线观看| 一二三四在线观看免费高清中文在线观看| 免费一级特黄特色大片在线观看| 日韩精品亚洲人成在线观看| 一区二区三区四区免费视频| 久久亚洲精品人成综合网| 亚州免费一级毛片| 亚洲狠狠婷婷综合久久久久| 在线看片免费人成视频福利| 免费永久看黄在线观看app| 三级片免费观看久久| 亚洲精品无码久久久久sm| 18禁无遮挡无码国产免费网站| 中文字幕无码亚洲欧洲日韩| 亚洲Av无码乱码在线观看性色| 99re6在线视频精品免费| 亚洲神级电影国语版| 日本黄色免费观看| 亚洲AV无码国产精品永久一区| 毛片免费观看网站| 欧亚一级毛片免费看| 免费**毛片在线播放直播 | 免费无遮挡无码永久视频| 亚洲 日韩经典 中文字幕 | 亚洲中文字幕在线第六区| 2021在线观看视频精品免费 | 国产午夜无码片免费|