为何hashlib.md5().hexdigest()与md5sum、openssl的MD5输出不一致?
Oh, I’ve run into this exact head-scratcher before! The core issue comes down to one tiny but critical detail: the echo command automatically adds a newline character (\n) to the end of its output, while your Python code calculates the MD5 of the raw string "test string" with no extra newline. Since MD5 hashes are tied directly to the exact bytes of input, these two different inputs produce totally different results.
Let me break this down step by step:
1. What’s happening in the shell
When you run echo "test string", the content being piped to md5sum or openssl dgst -md5 isn’t just "test string"—it’s "test string\n" (the original string plus a trailing newline). That’s why you get the hash f299060e0383392ebeac64b714eca7e3.
To fix this in the shell, use the -n flag with echo—this tells it not to append a newline:
echo -n "test string" | md5sum
Running this will spit out 6f8db599de986fab7a21625b7916589c, which matches your Python result perfectly.
2. What’s happening in Python
Your Python code md5("test string").hexdigest() calculates the MD5 of the exact, unmodified string "test string"—no hidden characters added. This is exactly what Gravatar expects: it requires the MD5 of the raw input (like an email address) without any extra whitespace or newlines introduced by shell tools.
To confirm the newline was the culprit, you can even replicate the shell’s behavior in Python by adding a newline to the string:
from hashlib import md5 md5("test string\n").hexdigest() # Returns f299060e0383392ebeac64b714eca7e3
This will produce the same hash as your original shell command, proving the newline was the missing piece.
Quick way to verify
If you want to see the raw bytes echo is outputting, use the od -c command to inspect them:
echo "test string" | od -c
You’ll clearly see the \n at the end of the output, which is the extra character causing the mismatch.
内容的提问来源于stack exchange,提问作者Mark C

