Kontroller om dit Password er Lækket med Python
Hvert evig eneste år hører vi om store datalækager, hvor millioner af brugeres adgangskoder fra diverse tjenester lander i hendene på kriminelle – og til sidst spredes offentligt på internettet. Have I Been Pwned (HIBP), skabt af sikkerhedsforskeren Troy Hunt, er den gyldne standard til at tjekke, om netop din adgangskode florerer derude blandt milliarder af lækkede linjer.
Men hvordan tjekker vi et kodeord, uden at give Troy Hunt vores kodeord? Det gør vi gennem en kryptografisk proces kaldet k-Anonymity.
I denne artikel forklarer vi konceptet og skriver et lille Python script, som du selv kan køre for at teste dine kodeord fuldstændig anonymt!
Er det sikkert at slå op? (k-Anonymity Modellen)
Når vi forespørger HaveIBeenPwned-databasen for at se om Password123! eksisterer, sender vi under ingen omstændigheder Password123! i ren tekst til deres server. Hvis API’et blev hacket i det øjeblik, ville angriberne jo netop se dit password.
I stedet benytter vi Hashing (som altid er en-vejs):
- Dit password (
Password123!) laves lokalt på din PC om til en usynlig SHA-1 hash-streng før det forlader huset. Eksempelvis bliver det til:CBFDAAC37CE3FDE8A5495FE8FC12EE4B25FBBEFA. - Vi sender nu KUN de første 5 tegn af hashet (
CBFDA) afsted til HIBP API’et. - Serveren hos HIBP søger deres masive database igennem for alle hashede data-læk, som starter med eksakt netop de 5 tegn, og returnerer en lang liste med alle hash-slutningerne der fuldfører stregen (Og de svarer ofte med 500+ forskellige match).
- Maskinen hos HIBP ved dermed kun, at du har adgangskode der deler præfix med 500 andre koder. De ved absolut ikke hvilken én.
- Din maskine og Python-scriptet sammenligner nu selv lokalt, om resten af din SHA-1 hash (de sidste 35 tegn) findes i listen over de returnerede hashes. C-I-A er fuldt og helt bevaret!
Python Adgangskode Checker (Script)
Her er koden, der implementerer præcis ovenstående k-Anonymity model, så du kan tjekke lynhurtigt fra din egen terminal.
Du skal bruge requests modulet (installeres med: pip install requests).
import hashlib
import requests
import sys
def request_api_data(query_char):
# Danner vores URL med de første 5 hash-karakterer
url = 'https://api.pwnedpasswords.com/range/' + query_char
res = requests.get(url)
# 200 = Success status-kode fra webserveren
if res.status_code != 200:
raise RuntimeError(f'Fejl: Serveren returnerede status {res.status_code}. Tjek AP-Iet.')
return res
def get_password_leaks_count(hashes, hash_to_check):
# Deler serverens rå svar-data op i det resterende hash, og count over hvor mange gange det er blevet lækket
hashes = (line.split(':') for line in hashes.text.splitlines())
for h, count in hashes:
if h == hash_to_check:
# Vi har fundet et eksakt lokalt match for vores adgangskode!
return count
return 0
def pwned_api_check(password):
# Hasher password med SHA-1 modulet og laver store bogstaver da API'et forventer det
sha1password = hashlib.sha1(password.encode('utf-8')).hexdigest().upper()
# Adskil de første 5 tegn og rest-tegnene
first5_chars, tail = sha1password[:5], sha1password[5:]
# Sender kun de 5 første tegn
response = request_api_data(first5_chars)
# Tjekker mod det modtagne datasæt om vores specifikke 'tail' befinder sig og matcher i listen.
return get_password_leaks_count(response, tail)
def main(args):
# Loop over alt input fra terminalen
for password in args:
count = pwned_api_check(password)
if count:
print(f'[ADVARSEL] Dit password "{password}" blev fundet lækket {count} gange... Du burde skifte det nu!')
else:
print(f'[SIKKER] "{password}" blev ikke fundet i HIBP databasen. Du burde være sikker!')
return 'Tjek afsluttet.'
if __name__ == '__main__':
# Henter passwords ind fra terminal-input under kørsel af script
# F.eks.: python pwned_check.py mitadgangskode123 qwertypassword
sys.exit(main(sys.argv[1:]))
Brug Python og en CLI som ovenstående for hurtigt i recon-fasen af sikkerhedstests eller i dit personlige sikkerheds-workflow at validere, om et kompromitteret password reelt set udgør en fare-zonen.
Kilder
- Have I Been Pwned: Pwned Passwords API - Den officielle tekniske dokumentation for API’et, der forklarer brugen af range-queries og k-Anonymity.
- Troy Hunt: Pwned Passwords, k-Anonymity and 141M New Passwords - Det originale blogindlæg fra skaberen af HIBP, som introducerede den anonyme opslagsmodel.
- Python Documentation: hashlib - Officiel reference for Pythons indbyggede bibliotek til hashing-algoritmer som SHA-1.
- Requests: HTTP for Humans - Dokumentation for det anvendte Python-bibliotek til at foretage HTTP-anmodninger til API’et.
> Quiz: Test din viden
1. Hvad er k-Anonymity i HIBP-sammenhæng?
2. Hvad returnerer HIBP-API'et til Python-scriptet?
3. Hvilken hash-algoritme bruges til at tjekke kodeordet mod HIBP?
4. Kan HIBP eller nogen anden se dit faktiske kodeord med k-Anonymity?