Cyberbezpieczeństwo w Go

Apr 29 2023
Zabezpiecz swoją aplikację za pomocą 10 fragmentów kodu Golang.
Wprowadzenie W tym artykule poznasz podstawowe funkcje Go, które są kluczowe przy tworzeniu bezpiecznych systemów. Należą do nich kryptografia, programowanie sieciowe i HTTP.
Wygenerowane przy użyciu Lexiki

Wstęp

W tym artykule poznasz podstawowe funkcje w Go, które są kluczowe przy tworzeniu bezpiecznych systemów. Należą do nich kryptografia, programowanie sieciowe i HTTP. Te funkcje są przydatne niezależnie od tego, czy tworzysz bezpieczną aplikację klient-serwer, zaszyfrowany system plików, czy aplikację internetową z protokołem SSL/TLS. Wykorzystanie tych funkcji może przyspieszyć realizację projektu i zagwarantować, że systemy będą niezawodne i bezpieczne.

crypto/rand.Przeczytaj

Aby wygenerować kryptograficznie bezpieczne liczby losowe, crypto/rand.Readmożna wykorzystać tę funkcję. Wymaga wycinka bajtów jako danych wejściowych i podaje liczbę zapisanych bajtów wraz z ewentualnym błędem (jeśli występuje). Przykład użycia go do generowania liczby losowej podano poniżej:

buf := make([]byte, 16)
_, err := rand.Read(buf)
if err != nil {
    panic(err)
}

Funkcja crypto/sha256.Sum256służy do obliczania skrótu SHA-256 wycinka bajtów. Funkcja pobiera wycinek bajtów jako dane wejściowe i zwraca 32-bajtową tablicę reprezentującą skrót SHA-256.

Oto przykład użycia crypto/sha256.Sum256do obliczenia skrótu SHA-256:

hash := sha256.Sum256([]byte("Hello, World!"))

Funkcja crypto/tls.Listennasłuchuje przychodzących połączeń TLS na określonym adresie i porcie. Funkcja przyjmuje jako dane wejściowe typ sieci, adres i tls.Configstrukturę oraz zwraca tls.Listenerinterfejs reprezentujący gniazdo nasłuchujące.

Oto przykład użycia crypto/tls.Listendo nasłuchiwania przychodzących połączeń TLS:

cert, err := tls.LoadX509KeyPair("cert.pem", "key.pem")
if err != nil {
    panic(err)
}

config := &tls.Config{
    Certificates: []tls.Certificate{cert},
}

ln, err := tls.Listen("tcp", ":443", config)
if err != nil {
    panic(err)
}
defer ln.Close()

Funkcja crypto/x509.ParseCertificatesłuży do analizowania certyfikatu X.509 z wycinka bajtów. Aby przeanalizować certyfikat, wprowadź fragment bajtu reprezentujący certyfikat X.509 do funkcji, która następnie zwróci strukturę reprezentującą przeanalizowany certyfikat.

Oto przykład użycia crypto/x509.ParseCertificatedo przeanalizowania certyfikatu X.509:

certData, err := ioutil.ReadFile("cert.pem")
if err != nil {
    panic(err)
}

cert, err := x509.ParseCertificate(certData)
if err != nil {
    panic(err)
}

Pakiet crypto/hmacudostępnia funkcje do implementacji algorytmów HMAC (ang. hash-based Message Authentication Code). Pakiet udostępnia funkcje do obliczania HMAC przy użyciu różnych funkcji skrótu, w tym SHA-1, SHA-256 i SHA-512.

Oto przykład użycia crypto/hmacdo obliczenia HMAC:

key := []byte("secret key")
message := []byte("Hello, World!")

mac := hmac.New(sha256.New, key)
mac.Write(message)
sum := mac.Sum(nil)

Pakiet crypto/cipherudostępnia funkcje do implementacji symetrycznych szyfrów blokowych , takich jak AES, DES i Blowfish. Ten pakiet oferuje różne funkcje do szyfrowania i odszyfrowywania danych za pomocą współdzielonego klucza.

Oto przykład użycia crypto/cipherdo szyfrowania i odszyfrowywania danych za pomocą AES:

key := []byte("secret key")
plaintext := []byte("Hello, World!")

block, err := aes.NewCipher(key)
if err != nil {
    panic(err)
}

ciphertext := make([]byte, aes.BlockSize+len(plaintext))
iv := ciphertext[:aes.BlockSize]
if _, err := io.ReadFull(rand.Reader, iv); err != nil {
    panic(err)
}

stream := cipher.NewCFBEncrypter(block, iv)
stream.XORKeyStream(ciphertext[aes.BlockSize:], plaintext)

// To decrypt
plaintext2 := make([]byte, len(plaintext))
stream = cipher.NewCFBDecrypter(block, iv)
stream.XORKeyStream(plaintext2, ciphertext[aes.BlockSize:])

Pakiet crypto/rsaudostępnia funkcje do implementacji algorytmu RSA, powszechnie używanego do szyfrowania i podpisów cyfrowych. Pakiet udostępnia funkcje do generowania kluczy RSA , szyfrowania i deszyfrowania danych oraz podpisywania i weryfikacji podpisów cyfrowych.

Oto przykład użycia crypto/rsado szyfrowania i odszyfrowywania danych przy użyciu RSA:

privateKey, err := rsa.GenerateKey(rand.Reader, 2048)
if err != nil {
    panic(err)
}

publicKey := &privateKey.PublicKey

plaintext := []byte("Hello, World!")
ciphertext, err := rsa.EncryptOAEP(sha256.New(), rand.Reader, publicKey, plaintext, nil)
if err != nil {
    panic(err)
}

plaintext2, err := rsa.DecryptOAEP(sha256.New(), rand.Reader, privateKey, ciphertext, nil)
if err != nil {
    panic(err)
}

Pakiet crypto/x509udostępnia funkcje do implementacji standardu X.509, powszechnie stosowanego dla certyfikatów SSL/TLS. Pakiet udostępnia funkcje do parsowania certyfikatów X.509, generowania certyfikatów X.509 oraz weryfikowania certyfikatów X.509.

Oto przykład użycia crypto/x509do przeanalizowania certyfikatu X.509:

certData, err := ioutil.ReadFile("cert.pem")
if err != nil {
    panic(err)
}

cert, err := x509.ParseCertificate(certData)
if err != nil {
    panic(err)
}

Pakiet crypto/ellipticudostępnia funkcje do implementacji kryptografii krzywych eliptycznych, powszechnie stosowanej do podpisów cyfrowych. Pakiet ten oferuje różne funkcje umożliwiające tworzenie i zarządzanie kluczami krzywych eliptycznych, a także podpisywanie i weryfikację podpisów cyfrowych.

Oto przykład użycia crypto/ellipticdo wygenerowania klucza krzywej eliptycznej i podpisania wiadomości:

privateKey, err := elliptic.GenerateKey(elliptic.P256(), rand.Reader)
if err != nil {
    panic(err)
}

publicKey := privateKey.PublicKey

message := []byte("Hello, World!")
r, s, err := ecdsa.Sign(rand.Reader, privateKey, message)
if err != nil {
    panic(err)
}

valid := ecdsa.Verify(&publicKey, message, r, s)
fmt.Println("Signature valid:", valid)

Pakiet net/httpudostępnia funkcje do implementacji serwerów i klientów HTTP. Pakiet udostępnia funkcje do wysyłania i odbierania żądań HTTP, analizowania odpowiedzi HTTP oraz zarządzania sesjami HTTP.

Oto przykład użycia do net/httpwysłania żądania HTTP GET i odebrania odpowiedzi:

resp, err := http.Get("https://www.example.com")
if err != nil {
    panic(err)
}
defer resp.Body.Close()

body, err := ioutil.ReadAll(resp.Body)
if err != nil {
    panic(err)
}

fmt.Println(string(body))