编程进阶网 编程进阶网
首页
  • 计算机原理
  • 操作系统
  • 网络协议
  • 数据库原理
  • 面向对象
  • 设计原则
  • 设计模式
  • 系统架构
  • 性能优化
  • 编程原理
  • 方案设计
  • 稳定可靠
  • 工程运维
  • 基础认知
  • 线性结构
  • 树与哈希
  • 工业级实现
  • 算法思想
  • 实战与综合
  • 算法题考核
  • C语言入门
  • C综合案例
  • C专栏博客
  • C标准集库
  • C++入门教程
  • C++综合案例
  • C++专栏博客
  • C++开发技巧
  • Java入门教程
  • Java综合案例
  • Java专栏博客
  • Go入门教程
  • Go综合案例
  • Go专栏博客
  • Go开发技巧
  • JavaScript入门
  • JavaScript高级
  • Android库解读
  • Android专栏
  • Android智能硬件
  • iOS ObjC入门
  • iOS Swift入门
  • iOS入门精通
  • Web之Html手册
  • Web之TypeScript
  • Web之Vue高级进阶
  • Linux之QML入门
  • Linux之QT核心库
  • Linux实践开发
  • Python教程
  • Shell&Bash教程
  • 工具脚本
  • 自动化脚本
  • 质量保障
  • 产品思考
  • 软实力
  • 开发流程
  • Git应用
  • 技术模版
  • 技术规范
  • Markdown
  • Mermaid
  • 开源协议
  • JSON工具
  • 文本工具
  • 图片处理
  • 文档转化
  • 代码压缩
  • 关于我
  • 自我精进
  • 职场管理
  • 职场面试
  • 心情杂货
  • 友情链接

杨充

专注编程 · 终身学习者
首页
  • 计算机原理
  • 操作系统
  • 网络协议
  • 数据库原理
  • 面向对象
  • 设计原则
  • 设计模式
  • 系统架构
  • 性能优化
  • 编程原理
  • 方案设计
  • 稳定可靠
  • 工程运维
  • 基础认知
  • 线性结构
  • 树与哈希
  • 工业级实现
  • 算法思想
  • 实战与综合
  • 算法题考核
  • C语言入门
  • C综合案例
  • C专栏博客
  • C标准集库
  • C++入门教程
  • C++综合案例
  • C++专栏博客
  • C++开发技巧
  • Java入门教程
  • Java综合案例
  • Java专栏博客
  • Go入门教程
  • Go综合案例
  • Go专栏博客
  • Go开发技巧
  • JavaScript入门
  • JavaScript高级
  • Android库解读
  • Android专栏
  • Android智能硬件
  • iOS ObjC入门
  • iOS Swift入门
  • iOS入门精通
  • Web之Html手册
  • Web之TypeScript
  • Web之Vue高级进阶
  • Linux之QML入门
  • Linux之QT核心库
  • Linux实践开发
  • Python教程
  • Shell&Bash教程
  • 工具脚本
  • 自动化脚本
  • 质量保障
  • 产品思考
  • 软实力
  • 开发流程
  • Git应用
  • 技术模版
  • 技术规范
  • Markdown
  • Mermaid
  • 开源协议
  • JSON工具
  • 文本工具
  • 图片处理
  • 文档转化
  • 代码压缩
  • 关于我
  • 自我精进
  • 职场管理
  • 职场面试
  • 心情杂货
  • 友情链接
  • ScriptHub 脚本工具箱
  • Python

  • Shell-Bash

  • 工具脚本

    • 工具脚本速查
    • 哈希校验
      • 一、Python 哈希计算
        • 1.1 字符串哈希(MD5 / SHA1 / SHA256)
        • 1.2 文件哈希——验证下载完整性
        • 1.3 HMAC——消息认证码(防篡改 + 身份验证)
        • 1.4 密码哈希——bcrypt(scrypt / argon2)
      • 二、Shell 一行哈希
      • 三、实战:文件完整性校验工具
    • Base64编码
    • AES加解密
    • RSA签名验签
    • JWT令牌
    • JSON与YAML
    • XML与CSV
    • 编码转义
    • 图片转换
    • 文档转换
    • 批量重命名
    • 分割合并
    • 目录同步
    • 文件监控
    • 压缩归档
    • 文件去重
    • cURL速查
    • HTTP调试
    • 端口DNS
    • 抓包代理
  • ScriptHub
  • 工具脚本
杨充
2022-06-10
目录

哈希校验

# 哈希校验

MD5/SHA1/SHA256 文件哈希、HMAC 消息认证码、文件完整性校验、密码哈希(bcrypt)——生产级脚本。

# 一、Python 哈希计算

# 1.1 字符串哈希(MD5 / SHA1 / SHA256)

#!/usr/bin/env python3
"""字符串哈希——一行生成摘要"""
import hashlib

def hash_string(text, algo='sha256'):
    """对字符串做哈希,返回十六进制字符串"""
    h = hashlib.new(algo)
    h.update(text.encode('utf-8'))
    return h.hexdigest()

# ---- 示例 ----
text = "Hello, 你好世界"
print("MD5:   ", hash_string(text, 'md5'))
print("SHA1:  ", hash_string(text, 'sha1'))
print("SHA256:", hash_string(text, 'sha256'))
print("SHA512:", hash_string(text, 'sha512'))
# 输出:
# MD5:    f228ee31a40cd94b0d239b6bad1ca43f
# SHA1:   cec1b98e4bc6cd39c2763ce7a6cdd1d3e00763e0
# SHA256: b6fd48fdd2a0f9caa3fa0c054f1b128567097c3b...
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20

# 1.2 文件哈希——验证下载完整性

#!/usr/bin/env python3
"""文件哈希——适合大文件(分块读取,不占内存)"""
import hashlib, sys

def file_hash(filepath, algo='sha256', chunk_size=8192):
    """计算文件哈希——分块读,大文件无压力"""
    h = hashlib.new(algo)
    with open(filepath, 'rb') as f:
        while True:
            chunk = f.read(chunk_size)
            if not chunk:
                break
            h.update(chunk)
    return h.hexdigest()

# ---- 命令行工具 ----
if __name__ == '__main__':
    if len(sys.argv) < 2:
        print(f"用法: {sys.argv[0]} <文件路径> [算法: sha256/md5/sha1/sha512]")
        sys.exit(1)

    path = sys.argv[1]
    algo = sys.argv[2] if len(sys.argv) > 2 else 'sha256'
    digest = file_hash(path, algo)
    print(f"{algo.upper()}: {digest}  {path}")
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25

# 1.3 HMAC——消息认证码(防篡改 + 身份验证)

HMAC = 哈希 + 密钥,用于验证消息在传输中未被篡改,同时证明来源身份:

#!/usr/bin/env python3
"""HMAC——带密钥的消息认证码"""
import hmac, hashlib

def hmac_sign(message, secret, algo='sha256'):
    """生成 HMAC 签名"""
    key = secret.encode('utf-8') if isinstance(secret, str) else secret
    msg = message.encode('utf-8') if isinstance(message, str) else message
    return hmac.new(key, msg, algo).hexdigest()

def hmac_verify(message, secret, signature, algo='sha256'):
    """验证 HMAC 签名——常量时间比较防时序攻击"""
    expected = hmac_sign(message, secret, algo)
    return hmac.compare_digest(expected, signature)  # 安全比较!

# ---- 示例:API 签名 ----
SECRET = "my-api-secret-key"
payload = '{"user":"alice","amount":100}'

sig = hmac_sign(payload, SECRET)
print(f"签名: {sig}")

# 模拟接收端验证
is_valid = hmac_verify(payload, SECRET, sig)
print(f"验证通过: {is_valid}")

# 模拟篡改检测
tampered = '{"user":"alice","amount":99999}'
is_valid2 = hmac_verify(tampered, SECRET, sig)
print(f"篡改检测: {is_valid2}")    # False——一击必现
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30

# 1.4 密码哈希——bcrypt(scrypt / argon2)

#!/usr/bin/env python3
"""密码存储——绝不能存明文或 MD5,用 bcrypt !"""
import bcrypt

# ---- 注册:哈希密码 ----
password = "user_password_123"
password_bytes = password.encode('utf-8')

# 生成 salt + 哈希(cost=12 表示 2^12 轮迭代)
hashed = bcrypt.hashpw(password_bytes, bcrypt.gensalt(rounds=12))
print(f"存入数据库: {hashed.decode()}")

# ---- 登录:验证密码 ----
login_attempt = "user_password_123"
is_correct = bcrypt.checkpw(login_attempt.encode('utf-8'), hashed)
print(f"密码正确: {is_correct}")                           # True

login_attempt_wrong = "wrong_password"
is_correct = bcrypt.checkpw(login_attempt_wrong.encode('utf-8'), hashed)
print(f"错误密码: {is_correct}")                           # False

# ⚠️ 为什么不用 SHA256(salt + password)?
#    SHA 太快了——攻击者可以每秒尝试百万次
#    bcrypt 故意慢——12 rounds 约 0.3秒/次
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24

# 二、Shell 一行哈希

#!/bin/bash

# ===== 字符串哈希 =====
echo -n "hello" | md5sum        # 5d41402abc4b2a76b9719d911017c592
echo -n "hello" | sha1sum       # aaf4c61ddcc5e8a2dabede0f3b482cd9aea9434d
echo -n "hello" | sha256sum     # 2cf24dba5fb0a30e26e83b2ac5b9e29e1b161e...

# ===== 文件哈希 =====
md5sum file.tar.gz               # MD5
sha1sum file.tar.gz              # SHA1
sha256sum file.tar.gz            # SHA256(推荐)
sha512sum file.tar.gz            # SHA512

# ===== 批量校验(.sha256 文件)=====
sha256sum -c file.tar.gz.sha256  # 自动读取校验文件

# ===== HMAC(用 openssl)=====
echo -n "message" | openssl dgst -sha256 -hmac "secret-key"

# ===== bcrypt 替代(用 htpasswd)=====
htpasswd -nbB alice "my_password" | cut -d: -f2
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21

# 三、实战:文件完整性校验工具

#!/usr/bin/env python3
"""
一键生成 + 验证文件校验和
用法:
  python hash_tool.py gen    dir/       # 生成所有文件的 sha256
  python hash_tool.py check  dir/       # 校验所有文件
"""
import os, sys, hashlib, json
from pathlib import Path

CHECKSUM_FILE = ".checksums.json"

def gen_checksums(root_dir):
    """递归生成目录下所有文件的 SHA256"""
    checksums = {}
    for path in Path(root_dir).rglob("*"):
        if path.is_file() and path.name != CHECKSUM_FILE:
            h = hashlib.sha256()
            with open(path, 'rb') as f:
                while chunk := f.read(65536):
                    h.update(chunk)
            checksums[str(path.relative_to(root_dir))] = h.hexdigest()
    with open(Path(root_dir) / CHECKSUM_FILE, 'w') as f:
        json.dump(checksums, f, indent=2)
    print(f"✅ 已生成 {len(checksums)} 个文件的校验和")

def check_checksums(root_dir):
    """校验目录下所有文件"""
    chk_path = Path(root_dir) / CHECKSUM_FILE
    if not chk_path.exists():
        print("❌ 未找到校验文件,请先运行 gen")
        return 1
    checksums = json.loads(chk_path.read_text())
    ok = fail = missing = 0
    for rel, expected in checksums.items():
        path = Path(root_dir) / rel
        if not path.exists():
            print(f"❌ 缺失: {rel}")
            missing += 1; continue
        h = hashlib.sha256()
        with open(path, 'rb') as f:
            while chunk := f.read(65536): h.update(chunk)
        if h.hexdigest() == expected: ok += 1
        else: print(f"❌ 校验失败: {rel}"); fail += 1
    print(f"✅ {ok} ok  ❌ {fail} fail  ⚠️ {missing} missing")
    return 0 if fail == 0 and missing == 0 else 1

if __name__ == '__main__':
    cmd = sys.argv[1] if len(sys.argv) > 1 else 'gen'
    root = sys.argv[2] if len(sys.argv) > 2 else '.'
    {'gen': gen_checksums, 'check': check_checksums}[cmd](root)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
#工具#加密
上次更新: 2026/06/17, 12:47:39
工具脚本速查
Base64编码

← 工具脚本速查 Base64编码→

最近更新
01
信号崩溃快速排查
06-15
02
CoreDump破案
06-15
03
perf火焰图实战
06-15
更多文章>
Theme by Vdoing | Copyright © 2019-2026 杨充 | MIT License | 桂ICP备2024034950号 | 桂公网安备45142202000030
  • 跟随系统
  • 浅色模式
  • 深色模式
  • 阅读模式