Skip to content

Commit

Permalink
Only use sha256
Browse files Browse the repository at this point in the history
Removed Hash function with other options
  • Loading branch information
stevenvegt committed Dec 13, 2024
1 parent a376d16 commit 5e53f51
Show file tree
Hide file tree
Showing 3 changed files with 35 additions and 131 deletions.
50 changes: 11 additions & 39 deletions did_x509/did_x509.go
Original file line number Diff line number Diff line change
@@ -1,9 +1,7 @@
package did_x509

import (
"crypto/sha1"
"crypto/sha256"
"crypto/sha512"
"crypto/x509"
"encoding/base64"
"errors"
Expand All @@ -15,38 +13,13 @@ import (

"github.com/nuts-foundation/go-did/did"
"github.com/nuts-foundation/uzi-did-x509-issuer/x509_cert"
"golang.org/x/crypto/sha3"
)

type HashAlg string
// hashAlg is the default hash algorithm used for hashing issuerCertificate
const hashAlg = "sha256"

const (
Sha1 HashAlg = "sha1"
Sha256 HashAlg = "sha256"
Sha384 HashAlg = "sha384"
Sha512 HashAlg = "sha512"
)

// Hash computes the hash of the input data using the specified algorithm.
// Supported algorithms include "sha1", "sha256", "sha384", and "sha512".
// Returns the computed hash as a byte slice or an error if the algorithm is not supported.
func Hash(data []byte, alg HashAlg) ([]byte, error) {
switch alg {
case Sha1:
sum := sha1.Sum(data)
return sum[:], nil
case Sha256:
sum := sha256.Sum256(data)
return sum[:], nil
case Sha384:
sum := sha3.Sum384(data)
return sum[:], nil
case Sha512:
sum := sha512.Sum512(data)
return sum[:], nil
}
return nil, fmt.Errorf("unsupported hash algorithm: %s", alg)
}
// newHashFn is the default hash function used for hashing issuerCertificate
var newHashFn = sha256.New

type X509Did struct {
Version string
Expand All @@ -57,14 +30,13 @@ type X509Did struct {

// FormatDid constructs a decentralized identifier (DID) from a certificate chain and an optional policy.
// It returns the formatted DID string or an error if the root certificate or hash calculation fails.
func FormatDid(issuerCert *x509.Certificate, hashAlg HashAlg, policy ...string) (*did.DID, error) {
issuerCertHash, err := Hash(issuerCert.Raw, hashAlg)
if err != nil {
return nil, err
}
func FormatDid(issuerCert *x509.Certificate, policy ...string) (*did.DID, error) {
hasher := newHashFn()
hasher.Write(issuerCert.Raw)
sum := hasher.Sum(nil)

encodeToString := base64.RawURLEncoding.EncodeToString(issuerCertHash)
fragments := []string{"did", "x509", "0", string(hashAlg), encodeToString}
b64EncodedHash := base64.RawURLEncoding.EncodeToString(sum[:])
fragments := []string{"did", "x509", "0", hashAlg, b64EncodedHash}
didString := strings.Join([]string{strings.Join(fragments, ":"), strings.Join(policy, "::")}, "::")
return did.ParseDID(didString)
}
Expand All @@ -86,7 +58,7 @@ func CreateDid(signingCert, caCert *x509.Certificate, subjectAttributes []x509_c

policies = append(policies, CreateSubjectPolicies(subjectTypes)...)

formattedDid, err := FormatDid(caCert, Sha256, policies...)
formattedDid, err := FormatDid(caCert, policies...)
return formattedDid, err
}

Expand Down
106 changes: 19 additions & 87 deletions did_x509/did_x509_test.go
Original file line number Diff line number Diff line change
@@ -1,82 +1,16 @@
package did_x509

import (
"bytes"
"crypto/sha1"
"crypto/sha256"
"crypto/sha512"
"crypto/x509"
"encoding/base64"
"fmt"
"strings"
"testing"

"github.com/nuts-foundation/go-did/did"
"github.com/nuts-foundation/uzi-did-x509-issuer/x509_cert"
"github.com/stretchr/testify/assert"
"golang.org/x/crypto/sha3"
)

func TestHash(t *testing.T) {
sha1sum := sha1.Sum([]byte("test"))
sha256sum := sha256.Sum256([]byte("test"))
sha384sum := sha3.Sum384([]byte("test"))
sha512sum := sha512.Sum512([]byte("test"))
testCases := []struct {
name string
data []byte
alg HashAlg
hash []byte
error error
}{
{
name: "SHA1",
data: []byte("test"),
alg: Sha1,
hash: sha1sum[:],
},
{
name: "SHA256",
data: []byte("test"),
alg: Sha256,
hash: sha256sum[:],
},
{
name: "SHA384",
data: []byte("test"),
alg: Sha384,
hash: sha384sum[:],
},
{
name: "SHA512",
data: []byte("test"),
alg: Sha512,
hash: sha512sum[:],
},
{
name: "Unsupported",
data: []byte("test"),
alg: "unsupported",
hash: nil,
error: fmt.Errorf("unsupported hash algorithm: %s", "unsupported"),
},
}

for _, tc := range testCases {
t.Run(tc.name, func(t *testing.T) {
hash, err := Hash(tc.data, tc.alg)
if tc.error != nil {
if err.Error() != tc.error.Error() {
t.Errorf("unexpected error %v, want %v", err, tc.error)
}
}
if !bytes.Equal(hash, tc.hash) {
t.Errorf("unexpected hash %x, want %x", hash, tc.hash)
}
})
}
}

func TestPercentEncode(t *testing.T) {
tests := []struct {
input string
Expand Down Expand Up @@ -111,12 +45,11 @@ func TestCreateDidSingle(t *testing.T) {
t.Fatal(err)
}

alg := Sha256
hash, err := Hash(rootCert.Raw, alg)
if err != nil {
t.Fatal(err)
}
rootHashString := base64.RawURLEncoding.EncodeToString(hash)
hash := newHashFn()
hash.Write(rootCert.Raw)
sum := hash.Sum(nil)

rootHashString := base64.RawURLEncoding.EncodeToString(sum[:])
types := []x509_cert.SanTypeName{x509_cert.SanTypeOtherName, x509_cert.SanTypePermanentIdentifierValue, x509_cert.SanTypePermanentIdentifierAssigner}

tests := []struct {
Expand All @@ -132,39 +65,39 @@ func TestCreateDidSingle(t *testing.T) {
name: "Happy path",
fields: fields{},
args: args{chain: chain},
want: did.MustParseDID(strings.Join([]string{"did", "x509", "0", string(alg), rootHashString, "", "san", "otherName", "A_BIG_STRING", "", "san", "permanentIdentifier.value", "A_PERMANENT_STRING", "", "san", "permanentIdentifier.assigner", "2.16.528.1.1007.3.3"}, ":")),
want: did.MustParseDID(strings.Join([]string{"did", "x509", "0", hashAlg, rootHashString, "", "san", "otherName", "A_BIG_STRING", "", "san", "permanentIdentifier.value", "A_PERMANENT_STRING", "", "san", "permanentIdentifier.assigner", "2.16.528.1.1007.3.3"}, ":")),
sanTypes: types,
errMsg: "",
},
{
name: "Happy path",
fields: fields{},
args: args{chain: chain},
want: did.MustParseDID(strings.Join([]string{"did", "x509", "0", string(alg), rootHashString, "", "san", "otherName", "A_BIG_STRING", "", "san", "permanentIdentifier.value", "A_PERMANENT_STRING"}, ":")),
want: did.MustParseDID(strings.Join([]string{"did", "x509", "0", hashAlg, rootHashString, "", "san", "otherName", "A_BIG_STRING", "", "san", "permanentIdentifier.value", "A_PERMANENT_STRING"}, ":")),
sanTypes: []x509_cert.SanTypeName{x509_cert.SanTypeOtherName, x509_cert.SanTypePermanentIdentifierValue},
errMsg: "",
},
{
name: "ok - with san othername",
fields: fields{},
args: args{chain: chain},
want: did.MustParseDID(strings.Join([]string{"did", "x509", "0", string(alg), rootHashString, "", "san", "otherName", "A_BIG_STRING"}, ":")),
want: did.MustParseDID(strings.Join([]string{"did", "x509", "0", hashAlg, rootHashString, "", "san", "otherName", "A_BIG_STRING"}, ":")),
sanTypes: []x509_cert.SanTypeName{x509_cert.SanTypeOtherName},
errMsg: "",
},
{
name: "ok - with san permanentIdentifier.value",
fields: fields{},
args: args{chain: chain},
want: did.MustParseDID(strings.Join([]string{"did", "x509", "0", string(alg), rootHashString, "", "san", "permanentIdentifier.value", "A_PERMANENT_STRING"}, ":")),
want: did.MustParseDID(strings.Join([]string{"did", "x509", "0", hashAlg, rootHashString, "", "san", "permanentIdentifier.value", "A_PERMANENT_STRING"}, ":")),
sanTypes: []x509_cert.SanTypeName{x509_cert.SanTypePermanentIdentifierValue},
errMsg: "",
},
{
name: "ok - with san permanentIdentifier.assigner",
fields: fields{},
args: args{chain: chain},
want: did.MustParseDID(strings.Join([]string{"did", "x509", "0", string(alg), rootHashString, "", "san", "permanentIdentifier.assigner", "2.16.528.1.1007.3.3"}, ":")),
want: did.MustParseDID(strings.Join([]string{"did", "x509", "0", hashAlg, rootHashString, "", "san", "permanentIdentifier.assigner", "2.16.528.1.1007.3.3"}, ":")),
sanTypes: []x509_cert.SanTypeName{x509_cert.SanTypePermanentIdentifierAssigner},
errMsg: "",
},
Expand Down Expand Up @@ -199,12 +132,11 @@ func TestCreateDidDouble(t *testing.T) {
t.Fatal(err)
}

alg := Sha256
hash, err := Hash(rootCert.Raw, alg)
if err != nil {
t.Fatal(err)
}
rootHashString := base64.RawURLEncoding.EncodeToString(hash)
hash := newHashFn()
hash.Write(rootCert.Raw)
sum := hash.Sum(nil)

rootHashString := base64.RawURLEncoding.EncodeToString(sum[:])
sanTypeNames := []x509_cert.SanTypeName{x509_cert.SanTypeOtherName, x509_cert.SanTypePermanentIdentifierValue, x509_cert.SanTypePermanentIdentifierAssigner}
sanTypeNamesShort := []x509_cert.SanTypeName{x509_cert.SanTypeOtherName}
subjectTypeNamesShort := []x509_cert.SubjectTypeName{x509_cert.SubjectTypeOrganization}
Expand All @@ -222,31 +154,31 @@ func TestCreateDidDouble(t *testing.T) {
name: "Happy path san",
fields: fields{},
args: args{chain: chain},
want: strings.Join([]string{"did", "x509", "0", string(alg), rootHashString, "", "san", "otherName", "A_BIG_STRING", "", "san", "permanentIdentifier.value", "A_SMALL_STRING", "", "san", "permanentIdentifier.assigner", "2.16.528.1.1007.3.3"}, ":"),
want: strings.Join([]string{"did", "x509", "0", hashAlg, rootHashString, "", "san", "otherName", "A_BIG_STRING", "", "san", "permanentIdentifier.value", "A_SMALL_STRING", "", "san", "permanentIdentifier.assigner", "2.16.528.1.1007.3.3"}, ":"),
sanTypes: sanTypeNames,
errMsg: "",
},
{
name: "Happy path short san",
fields: fields{},
args: args{chain: chain},
want: strings.Join([]string{"did", "x509", "0", string(alg), rootHashString, "", "san", "otherName", "A_BIG_STRING"}, ":"),
want: strings.Join([]string{"did", "x509", "0", hashAlg, rootHashString, "", "san", "otherName", "A_BIG_STRING"}, ":"),
sanTypes: sanTypeNamesShort,
errMsg: "",
},
{
name: "Happy path short san",
fields: fields{},
args: args{chain: chain},
want: strings.Join([]string{"did", "x509", "0", string(alg), rootHashString, "", "subject", "O", "FauxCare"}, ":"),
want: strings.Join([]string{"did", "x509", "0", hashAlg, rootHashString, "", "subject", "O", "FauxCare"}, ":"),
subjectTypes: subjectTypeNamesShort,
errMsg: "",
},
{
name: "Happy path mixed",
fields: fields{},
args: args{chain: chain},
want: strings.Join([]string{"did", "x509", "0", string(alg), rootHashString, "", "san", "otherName", "A_BIG_STRING", "", "subject", "O", "FauxCare"}, ":"),
want: strings.Join([]string{"did", "x509", "0", hashAlg, rootHashString, "", "san", "otherName", "A_BIG_STRING", "", "subject", "O", "FauxCare"}, ":"),
sanTypes: sanTypeNamesShort,
subjectTypes: subjectTypeNamesShort,
errMsg: "",
Expand Down
10 changes: 5 additions & 5 deletions pem/pem_reader_test.go
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
package pem

import (
"crypto/sha256"
"encoding/base64"
"log"
"os"
"strings"
"testing"

"github.com/nuts-foundation/uzi-did-x509-issuer/did_x509"
"github.com/nuts-foundation/uzi-did-x509-issuer/x509_cert"
"github.com/stretchr/testify/assert"
)
Expand Down Expand Up @@ -114,15 +114,15 @@ func TestParseFileOrPath(t *testing.T) {
dataMap := make(map[string][]byte)
for i := 0; i < len(data); i++ {
bytes := (data)[i]
hash, err := did_x509.Hash(bytes, "sha512")
sum := sha256.Sum256(bytes)
failError(t, err)
dataMap[base64.RawURLEncoding.EncodeToString(hash)] = bytes
dataMap[base64.RawURLEncoding.EncodeToString(sum[:])] = bytes
}
for i := 0; i < len(certs); i++ {
bytes := (certs)[i].Raw
hash, err := did_x509.Hash(bytes, "sha512")
sum := sha256.Sum256(bytes)
failError(t, err)
fileBytes := dataMap[base64.RawURLEncoding.EncodeToString(hash)]
fileBytes := dataMap[base64.RawURLEncoding.EncodeToString(sum[:])]
ok := assert.Equal(t, bytes, fileBytes)
if !ok {
t.Fail()
Expand Down

0 comments on commit 5e53f51

Please sign in to comment.