Python使用license设置项目有效期

转载
Python使用license设置项目有效期

目录

python项目使用license

1、将MAC和使用期限加密生成license
2、校验license文件
3、Django项目结合中间件设置license

1、将MAC和使用期限加密生成license

代码示例:create_license_file.py


```python
from binascii import b2a_hex
from Crypto.Cipher import AES

aesKey = b'2021052020210520'  # 加密与解密所使用的密钥,长度必须是16的倍数
aesIv = b'2021052020210520'  # initial Vector,长度要与aesKey一致
aesMode = AES.MODE_CBC  # 使用CBC模式


def encrypt(content):
    """ 将MAC地址和Date进行加密 """

    # 读取加密内容,并处理成16位的倍数
    while len(content) % 16:
        content += ' '
    content = content.encode('utf-8')

    # 对物理地址和license期限进行加密
    aes = AES.new(aesKey, aesMode, aesIv)
    encrypted_content = aes.encrypt(content)

    return (b2a_hex(encrypted_content))


def gen_license_file(mac, license_time_limit):
    """ 生成license文件 """
    license_file = './License.dat'

    with open(license_file, 'w') as LF:
        LF.write('MAC : ' + mac + '\n')
        LF.write('Date : ' + license_time_limit + '\n')

        sign = encrypt(mac + '#' + license_time_limit)
        LF.write('Sign : ' + str(sign.decode('utf-8')) + '\n')


if __name__ == '__main__':
    # MAC地址
    mac = '3c:ec:ef:3a:a8:67'
    # license使用期限
    license_time_limit = '20220522'
    # 生成license文件
    gen_license_file(mac, license_time_limit)

2、校验license文件

代码示例:parse_license.py

import re
import sys
import uuid
import datetime
from binascii import a2b_hex
from Crypto.Cipher import AES

aesKey = b'2021052020210520'     # 加密与解密所使用的密钥,长度必须是16的倍数
aesIv = b'2021052020210520'      # initial Vector,长度要与aesKey一致
aesMode = AES.MODE_CBC          # 使用CBC模式


class LicenseCheck():
    def start_check(self):
        license_dic = self.parse_license_file()
        sign = self.decrypt(license_dic['Sign'])

        sign_list = sign.split('#')
        mac = sign_list[0].strip()
        date = sign_list[1].strip()

        # 校验license文件MAC地址和Date是否被手动更改
        if (mac != license_dic['MAC']) or (date != license_dic['Date']):
            print('*Error*: License file is modified!')
            sys.exit(1)

        if len(sign_list) == 2:
            mac = self.get_mac()  # 获取服务器MAC地址
            current_date = datetime.datetime.now().strftime('%Y%m%d')  # 获取当前时间

            # 校验物理地址是否正确
            print("permission_mac:", sign_list[0])
            print("current_mac:", mac)
            if sign_list[0] != mac:
                print('*Error*: Invalid host!')
                sys.exit(1)

            # 检验license文件是否过期
            print("permission_date:", sign_list[1])
            print("current_date:", current_date)
            if sign_list[1] <= current_date:
                print('*Error*: License is expired!')
                sys.exit(1)

        else:
            print('*Error*: Wrong Sign setting on license file.')
            sys.exit(1)


    def parse_license_file(self):
        """ 解析license文件 """

        license_dic = {}
        license_file = './License.dat'

        with open(license_file, 'r') as LF:
            for line in LF.readlines():
                if re.match('^\s*(\S+)\s*:\s*(\S+)\s*$', line):
                    my_match = re.match('^\s*(\S+)\s*:\s*(\S+)\s*$', line)
                    license_dic[my_match.group(1)] = my_match.group(2)

        return (license_dic)


    def decrypt(self, content):
        """ 解密license文件 """
        aes = AES.new(aesKey, aesMode, aesIv)
        decrypted_content = aes.decrypt(a2b_hex(content.encode('utf-8')))

        return (decrypted_content.decode('utf-8'))


    def get_mac(self):
        """ 获取服务器MAC地址 """
        mac = uuid.UUID(int=uuid.getnode()).hex[-12:]
        return ":".join([mac[e:e + 2] for e in range(0, 11, 2)])


def function():
    """ 测试license是否校验通过 """
    print('license is ok!')


if __name__ == '__main__':
    license_check_obj = LicenseCheck()
    license_check_obj.start_check()
    function()

3、Django项目结合中间件设置license

代码示例:my_middleware.py

import re
import uuid
import datetime
from binascii import a2b_hex
from Crypto.Cipher import AES

from django.http import JsonResponse
from utils.common_utils import restore_initial
from django.utils.deprecation import MiddlewareMixin

aesKey = b'2021052020210520'  # 加密与解密所使用的密钥,长度必须是16的倍数
aesIv = b'2021052020210520'  # initial Vector,长度要与aesKey一致
aesMode = AES.MODE_CBC  # 使用CBC模式


class LicenseCheck():
    def start_check(self):
        """ 开始检验license """

        license_dic = self.parse_license_file()
        sign = self.decrypt(license_dic['Sign'])

        sign_list = sign.split('#')
        mac = sign_list[0].strip()
        date = sign_list[1].strip()

        # 校验license文件MAC地址和Date是否被手动更改
        if (mac != license_dic['MAC']) or (date != license_dic['Date']):
            print('*License Error*: License file is modified!')
            return {'code': '0', 'msg': '*License Error*: License file is modified!'}

        if len(sign_list) == 2:
            mac = self.get_mac()  # 获取服务器MAC地址
            current_date = datetime.datetime.now().strftime('%Y%m%d')  # 获取当前时间

            # 校验物理地址是否正确
            print("permission_mac:", sign_list[0])
            print("current_mac:", mac)
            if sign_list[0] != mac:
                print('*License Error*: Invalid host!')
                return {'code': '0', 'msg': '*License Error*: Invalid host!'}

            # 检验license文件是否过期
            print("permission_date:", sign_list[1])
            print("current_date:", current_date)
            if sign_list[1] <= current_date:
                print('*License Error*: License is expired!')
                return {'code': '0', 'msg': '*License Error*: License is expired!'}

        else:
            print('*License Error*: Wrong Sign setting on license file.')
            return {'code': '0', 'msg': '*License Error*: Wrong Sign setting on license file.'}

    def parse_license_file(self):
        """ 解析license文件 """

        license_dic = {}
        license_file = 'License.dat'

        try:
            with open(license_file, 'r') as LF:
                for line in LF.readlines():
                    if re.match('^\s*(\S+)\s*:\s*(\S+)\s*$', line):
                        my_match = re.match('^\s*(\S+)\s*:\s*(\S+)\s*$', line)
                        license_dic[my_match.group(1)] = my_match.group(2)
        except Exception as e:
            print('*License Error*: License文件不存在')
            return {'code': '0', 'msg': '*License Error*: License文件不存在.', 'data': str(e)}

        return (license_dic)

    def decrypt(self, content):
        """ 解密license文件 """
        aes = AES.new(aesKey, aesMode, aesIv)
        decrypted_content = aes.decrypt(a2b_hex(content.encode('utf-8')))
        
        return (decrypted_content.decode('utf-8'))

    def get_mac(self):
        """ 获取服务器MAC地址 """
        mac = uuid.UUID(int=uuid.getnode()).hex[-12:]
        return ":".join([mac[e:e + 2] for e in range(0, 11, 2)])


class LicenseCheckMiddleware(MiddlewareMixin):
    """ License校验中间件 """

    def process_request(self, request):
        license_check_obj = LicenseCheck()
        res_data = license_check_obj.start_check()
        if res_data and res_data.get('code') == '0':
            return JsonResponse({"code": 0, "msg": res_data.get('msg', ''), "data": res_data.get('data', '')})
  • 0
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
Python项目中,使用license(许可证)非常重要。许可证是一种法律文档,它确定了软件使用者对软件的许可范围和条件。 Python社区提供了许多不同类型的license开发者选择。其中最常见的是MIT、BSD、Apache、GPL等。每种license都有自己的特点和限制。选择合适的license对于项目的发展和使用非常关键。 MIT和BSD是最宽松的license类型之一。它们允许用户以任何目的使用、修改和分发软件,同时也不强制用户必须发布源代码。这使得这些license非常适合商业项目或闭源项目。 Apache license也是一种较为宽松的license,允许用户自由使用、修改和分发软件。与MIT和BSD略有不同的是,Apache license需要在源代码中包含原始的copyright和license声明。 相比之下,GPL(通用公共许可证)是一种更加严格的license类型。如果项目使用了GPL许可证,那么在使用、修改或分发软件时,用户必须将其派生作品也以GPL许可证发布。这意味着任何使用GPL软件的项目都必须开源并提供源代码。 在选择license时,开发者需要考虑项目的具体情况和目标。如果希望将软件用于商业目的或不愿意公开源代码,那么MIT或BSD可能是更好的选择。而如果希望软件尽可能自由地传播和共享,并且希望贡献给开源社区,那么更加严格的GPL可能是更适合的许可证。 总之,选择适当的license对于Python项目的成功与否至关重要。开发者应该仔细考虑不同license类型的限制和影响,并选择最符合项目需求的license。这样可以确保项目的合法性、可持续性和自由度。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值