当前位置: 移动技术网 > IT编程>脚本编程>Python > 验证客户端的链接合法性

验证客户端的链接合法性

2018年11月28日  | 移动技术网IT编程  | 我要评论

黑道王子的99号天使,卖春堂,真天线无双

什么是验证合法性?

即在客户端想要和客户端进行链接的时候, 我们对客户端的身份进行验证是否合法. 

我们如果想在分布式系统中实现一个简单的客户端链接认证功能, 但是又不想ssl那么复杂, 那么我们可以利用hmac + 加盐的方式来实现.

首先介绍两个方法,:

1. os.urandom(n)

该方法是一种bytes类型的随机生成n个字节字符串的方法, 而且每次生成的值都不相同.

import hmac
message = b'hello world'
key = b'secret'
h = hmac.new(key,message,digestmod='md5')
print(h.hexdigest())
#比较两个密文是否相同,可以用hmac.compare_digest(密文、密文),然会true或者false。
os.urandom用法示例

 2.hmac:

我们之前了解了用hashlib进行md5加密. 该方法其实和它差不多.

python自带的hmac模块实现了标准的hmac算法, 我们首先需要准备待计算的原始消息message,随机key和哈希算法, 这里采用md5算法.

具体使用方法如下:

import hmac
message = b'hello world'
key = b'secret'
h = hmac.new(key,message,digestmod='md5')
print(h.hexdigest())
#比较两个密文是否相同,可以用hmac.compare_digest(密文、密文),然会true或者false。
hmac用法示例

 hmac输出的长度和原始哈希算法的长度一致。需要注意传入的key和message都是bytes类型,str类型需要首先编码为bytes

下面是利用hmac+加盐的方式来实现一个简单的客户端链接认证功能的例子:

from socket import *
import hmac, os

secret_key = b"hello, world!"

def conn_auth(conn):
    """
    认证客户端链接
    :param conn:
    :return: 验证结果
    """
    print("开始验证新连接的合法性")
    msg=os.urandom(32)  # 生成一个32字节的随机字符串
    conn.sendall(msg)
    h = hmac.new(secret_key, msg)   # 生成密文
    digest = h.digest()
    respone = conn.recv(len(digest))
    return hmac.compare_digest(digest, respone) # 返回结果true或者false

def data_handler(conn, bufsize=1024):
    """
    根据验证结果, 判断是否通信
    :param conn:
    :param bufsize:
    :return:
    """
    if not conn_auth(conn):
        print("链接不合法,关闭链接")
        conn.close()
        return
    print("链接合法, 开始通信")
    while true:
        data = conn.recv(bufsize)
        if not data:break
        conn.sendall(data.upper())

def server_handler(ip_port, bufsize, backlog=5):
    """
    只处理链接
    :param ip_port:
    :param bufsize:
    :param backlog:
    :return:
    """
    tcp_socket_server=socket(af_inet, sock_stream)
    tcp_socket_server.bind(ip_port)
    tcp_socket_server.listen(backlog)
    while 1:
        conn, addr = tcp_socket_server.accept()
        print("新连接[%s, %s]" %(addr[0],addr[1]))
        data_handler(conn, bufsize)


if __name__ == '__main__':
    ip_port = ("127.0.0.1", 8808)
    bufsize = 1024
    server_handler(ip_port, bufsize)
验证合法性链接_服务端
from socket import *
import hmac, os

secret_key = b"hello, world!"

def conn_auth(conn):
    """
    接收服务端的随机码, 加密后发给服务端
    :param conn:
    :return:
    """
    msg = conn.recv(32)
    h = hmac.new(secret_key, msg)
    digest = h.digest()
    conn.sendall(digest)


def client_handler(ip_port, bufsize):
    """
    创建tcp下的socket, 与服务端通信
    :param ip_port:
    :param bufsize:
    :return:
    """
    tcp_socket_client = socket(af_inet, sock_stream)
    tcp_socket_client.connect(ip_port)
    conn_auth(tcp_socket_client)

    while 1:
        data = input(">>>:").strip()
        if not data:continue
        if data == "quit":break
        tcp_socket_client.sendall(data.encode("utf-8"))
        respone = tcp_socket_client.recv(bufsize)
        print(respone.decode("utf-8"))

if __name__ == '__main__':
    ip_port = ("127.0.0.1", 8808)
    bufsize = 1024
    client_handler(ip_port, bufsize)
验证合法性链接_客户端

 

如对本文有疑问,请在下面进行留言讨论,广大热心网友会与你互动!! 点击进行留言回复

相关文章:

验证码:
移动技术网