zoukankan      html  css  js  c++  java
  • lua脚本之钉钉免密登录

    nginx.conf

    worker_processes  1;
    error_log logs/error.log;
    events {
        worker_connections 1024;
    }
    http {
        resolver 8.8.8.8;
        server {
            listen 8080;
            location / {
                default_type text/html;
                charset utf-8;
                lua_code_cache on;
                #rewrite_by_lua_file /example/rewrite.lua;
                access_by_lua_file /example/root_auth.lua;
                proxy_pass https://tieba.baidu.com/;
            }
            location /auth {
                default_type text/html;
                charset utf-8;
                lua_code_cache on;
                #rewrite_by_lua_file /example/rewrite.lua;
                #access_by_lua_file /example/yidong.lua;
                access_by_lua_file /example/end.lua;
            }
        }
    }

    end.lua

    local http = require "resty.http"
    local httpc = http.new()
    local mysql = require "resty.mysql"
    local cjson = require "cjson"
    local b64 = require "base64"
    local luaConfig = require("lua_config")
    
    
    local appid=luaConfig.ding_account.appid
    local appsecret=luaConfig.ding_account.appsecret
    local AppKey=luaConfig.ding_account.AppKey
    local AppSecret=luaConfig.ding_account.AppSecret
    
    local request_uri = ngx.var.request_uri
    local request_method = ngx.var.request_method
    local dingauth=ngx.var.cookie_dingauth
    
    function isCooike()
        if dingauth ~= nil then
            local dingauth_e=b64.dec(dingauth)
            if cjson.decode(dingauth_e)["cookie_token"]=="3MiOiJuaW5naGFvLm5ldCIsImVE0Mzg5NTU0NDUiLC" then
                ngx.update_time()
                if cjson.decode(dingauth_e)["start_time"] + 5 > ngx.time() then
                    local s,e=string.find(request_uri, "?")
                    local n_uri=nil
                    if s~=nil then
                        n_uri=string.sub(request_uri,1,s-1)
                    else
                        n_uri=request_uri
                    end
                    n_uri=string.gsub(n_uri,"/auth","")
                    local u_uri=nil
                    if n_uri == "" then
                        u_uri=string.gsub(request_uri,"/auth","/")
                    else
                        u_uri=string.gsub(request_uri,"/auth","")
                    end
                    ngx.redirect(u_uri)
                end
            end
        end
    end
    
    function isMobile(userAgent)
        local mobile = {
                    "phone", "android", "mobile", "itouch", "ipod", "symbian", "htc", "palmos", "blackberry", "opera mini", "windows ce", "nokia", "fennec",
                    "hiptop", "kindle", "mot", "webos", "samsung", "sonyericsson", "wap", "avantgo", "eudoraweb", "minimo", "netfront", "teleca"
                }
        userAgent = string.lower(userAgent)
        for i, v in ipairs(mobile) do
            if string.match(userAgent, v) then
                return true
            end
        end
        return false
    end
    
    function get(url)
        local res, err = httpc:request_uri(url,
        {
        ssl_verify = false,
        method = "GET",
        body = "",
        headers = {
           ['Content-Type']="application/json;charset=UTF-8"
             }
        })
        return res,err
    end
    
    function post(url,body)
        local res, err = httpc:request_uri(url,
        {
        ssl_verify = false,
        method = "POST",
        body = body,
        headers = {
           ['Content-Type']="application/json;charset=UTF-8"
             }
        })
        return res,err
    end
    
    function get_tooken()
        local res,err=get(string.format("https://oapi.dingtalk.com/sns/gettoken?appid=%s&appsecret=%s",appid,appsecret))
        return res.body
    end
    
    function dingCallBack(scheme,server_ip,port,l_uri,uir_enb64)
        ding_uri=string.format("https://oapi.dingtalk.com/connect/oauth2/sns_authorize?appid=dingoa3fbgkiif8mq9y8jf&response_type=code&scope=snsapi_auth&redirect_uri=%s://%s:%s%s?%s=1",scheme,server_ip,port,l_uri,uir_enb64)
        ngx.redirect(ding_uri)
    end
    
    function dingAuth()
    tooken_ret=get_tooken()
    --{"errcode":0,"access_token":"b7e87fc6cced35ff8f01901c5ae0fa6b","errmsg":"ok","expires_in":7200}
    if cjson.decode(tooken_ret)['errcode'] then
        yy_token=cjson.decode(tooken_ret)['access_token']
    else
        ngx.say(cjson.encode({status=false,msg="token 获取失败"}))
    end
    -- 获取用户信息
    local user_info_url = string.format("https://oapi.dingtalk.com/sns/get_persistent_code?access_token=%s",yy_token)
    local data={tmp_auth_code = code}
    local res,err=post(user_info_url,cjson.encode(data))
    if cjson.decode(res.body)['errcode']==0 then
        unionid=cjson.decode(res.body)['unionid']
        --深奎
        A_res,A_err=get(string.format("https://oapi.dingtalk.com/gettoken?appkey=%s&appsecret=%s",AppKey,AppSecret))
        if cjson.decode(A_res.body)["errcode"]==0 then
            A_tooken=cjson.decode(A_res.body)["access_token"]
            uid_url=string.format("https://oapi.dingtalk.com/user/getUseridByUnionid?access_token=%s&unionid=%s",A_tooken,unionid)
            local res,err=get(uid_url)
            if cjson.decode(res.body)["errcode"]==0 then
                --u_info_uri=string.format("https://oapi.dingtalk.com/user/get?access_token=%s&userid=%s",A_tooken,cjson.decode(res.body)["userid"])
                --local U_info_res,U_info_err=get(u_info_uri)
                --if cjson.decode(U_info_res.body)["errcode"]==0 then
                --    local mail=cjson.decode(U_info_res.body)["email"]
                --    if mail == nil then
                --        ngx.print("没有权限获取邮箱信息")
                --    elseif mail == "" then
                --        ngx.print("钉钉中没有邮箱信息")
                --    end
                --    ngx.print(mail)
                --else
                --    ngx.print("获取mail失败")
                --end
                local remote_uri=nil
                for k,v in pairs(ngx.req.get_uri_args()) do
                    if string.match(k, "DZMSSlIBgrZt6")=="DZMSSlIBgrZt6" then
                        remote_all=b64.dec(string.gsub(k,"DZMSSlIBgrZt6",""))
                        remote_arg=cjson.decode(remote_all)["remote_arg"]
                        remote_uri=cjson.decode(remote_all)["remote_uri"]
                    end
                end
                if remote_uri ~= nil then
                    remote_uri=string.gsub(remote_uri,"/auth","")
                    if remote_uri=="" then
                        remote_uri="/"
                    end
                    remote_arg_d=cjson.decode(remote_arg)
                    remote_arg_d["code"]="1"
                    local arg_str=""
                    local nb=1
                    for key, value in pairs(remote_arg_d) do
                          if nb==1 then
                              arg_str=string.format("?%s%s=%s",arg_str,key,value)
                          else
                             arg_str=string.format("%s&%s=%s",arg_str,key,value)
                          end
                          nb=nb+1
                    end
                    --ngx.print(string.format("%s%s",remote_uri,arg_str))
                    ngx.redirect(string.format("%s%s",remote_uri,arg_str))
                else
                    ngx.print("nil")
                end
            else
               ngx.say(cjson.encode({status=false,msg="企业下未找到该用户"}))
                --return cjson.encode({status=false})
            end
        else
            ngx.say(cjson.encode({status=false,msg="全局tooken获取失败"}))
        end
    else
        ngx.say(cjson.encode({status=false,msg="获取用户unionid失败"}))
    end
    end
    
    isCooike()
    local userAgent = ngx.req.get_headers().user_agent
    local ismobile = isMobile(userAgent)
    if "GET"==request_method then
        code = ngx.req.get_uri_args()["code"] or 0
        if code == 0 then
            if ismobile then
                local port=ngx.var.server_port
                local scheme=ngx.var.scheme
                local server_ip="10.10.80.21"
                local s,e=string.find(request_uri, "?")
                local u_a={}
                remote_uri=nil
                if s~=nil then
                    remote_uri=string.sub(request_uri,1,s-1)
                end
                u_a["remote_uri"]=request_uri
                u_a["remote_arg"]=cjson.encode(ngx.req.get_uri_args())
                local uir_enb64=b64.enc(cjson.encode(u_a))
                uir_enb64=string.format("DZMSSlIBgrZt6%s",uir_enb64)
                dingCallBack(scheme,server_ip,port,"/auth",uir_enb64)
            else
                ngx.print("是PC端")
            end
        else
            --ngx.print("拿到code")
            dingAuth()
        end
    end

    base64.lua

    base64 = {}
    
    local b='ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/'
    -- You will need this for encoding/decoding
    -- encoding
    function base64.enc(data)
        return ((data:gsub('.', function(x)
            local r,b='',x:byte()
            for i=8,1,-1 do r=r..(b%2^i-b%2^(i-1)>0 and '1' or '0') end
            return r;
        end)..'0000'):gsub('%d%d%d?%d?%d?%d?', function(x)
            if (#x < 6) then return '' end
            local c=0
            for i=1,6 do c=c+(x:sub(i,i)=='1' and 2^(6-i) or 0) end
            return b:sub(c+1,c+1)
        end)..({ '', '==', '=' })[#data%3+1])
    end
    
    -- decoding
    function base64.dec(data)
        data = string.gsub(data, '[^'..b..'=]', '')
        return (data:gsub('.', function(x)
            if (x == '=') then return '' end
            local r,f='',(b:find(x)-1)
            for i=6,1,-1 do r=r..(f%2^i-f%2^(i-1)>0 and '1' or '0') end
            return r;
        end):gsub('%d%d%d?%d?%d?%d?%d?%d?', function(x)
            if (#x ~= 8) then return '' end
            local c=0
            for i=1,8 do c=c+(x:sub(i,i)=='1' and 2^(8-i) or 0) end
                return string.char(c)
        end))
    end
    return base64

    lua_config.lua

    local config_table={}
    config_table.ip='xxx'
    config_table.port=xxx
    config_table.password='xxx'
    config_table.dingding_site={"xxx","xxx"}
    
    
    local ding_account={}
    ding_account["appid"]="xxx"   --免登的id
    ding_account["appsecret"]="xxxx"  --免登的secret
    ding_account["AppKey"]="xxx"    --有通讯录权限的应用appkey
    ding_account["AppSecret"]="xxx"  --有通讯录权限的应用secret
    config_table.ding_account=ding_account
    
    return config_table

    root_auth.lua

    local http = require "resty.http"
    local httpc = http.new()
    local cjson = require "cjson"
    local b64 = require "base64"
    local request_method = ngx.var.request_method
    --ngx.header['Set-Cookie'] = 'dingauth=cookie; path=/; Expires=' .. ngx.cookie_time(ngx.time() + 1 * 5)
    --ngx.print(ngx.var.http_cookie)
    local dingauth=ngx.var.cookie_dingauth
    local cookie={}
    if "GET"==request_method then
        code = ngx.req.get_uri_args()["code"] or 0
        if code == "1" then
            ngx.update_time()
            cookie["start_time"]=ngx.time()
            cookie["cookie_token"]="3MiOiJuaW5naGFvLm5ldCIsImVE0Mzg5NTU0NDUiLC"
            cookie_str=b64.enc(cjson.encode(cookie))
            ngx.header['Set-Cookie'] = string.format('dingauth=%s; path=/; Expires=',cookie_str) .. ngx.cookie_time(ngx.time() + 1 * 5)
        else
            if dingauth == nil then
                ngx.print("没有cookie")
            else
                local dingauth_e=b64.dec(dingauth)
                if cjson.decode(dingauth_e)["cookie_token"]=="3MiOiJuaW5naGFvLm5ldCIsImVE0Mzg5NTU0NDUiLC" then
                    local zw="zw"
                end
            end
        end
    end

    图:

  • 相关阅读:
    bzoj3527: [Zjoi2014]力 fft
    bzoj3295: [Cqoi2011]动态逆序对 cdq分治
    快速读入fread
    km板子(二分图最大权匹配)
    spfa毒瘤算法
    牛客网暑期ACM多校训练营(第三场)DEncrypted String Matching fft
    P4173 残缺的字符串 fft
    圆和多边形交模板
    hdu多校2C
    Codeforces Round #449 (Div. 1)C
  • 原文地址:https://www.cnblogs.com/zhangkui/p/11009385.html
Copyright © 2011-2022 走看看