github.com/adnan-c/fabric_e2e_couchdb@v0.6.1-preview.0.20170228180935-21ce6b23cf91/accesscontrol/attributes/attributes_test.go (about) 1 /* 2 Copyright IBM Corp. 2016 All Rights Reserved. 3 4 Licensed under the Apache License, Version 2.0 (the "License"); 5 you may not use this file except in compliance with the License. 6 You may obtain a copy of the License at 7 8 http://www.apache.org/licenses/LICENSE-2.0 9 10 Unless required by applicable law or agreed to in writing, software 11 distributed under the License is distributed on an "AS IS" BASIS, 12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 See the License for the specific language governing permissions and 14 limitations under the License. 15 */ 16 17 package attributes 18 19 import ( 20 "bytes" 21 "crypto/x509" 22 "encoding/pem" 23 "fmt" 24 25 "io/ioutil" 26 "os" 27 "strings" 28 "testing" 29 30 "github.com/golang/protobuf/proto" 31 pb "github.com/hyperledger/fabric/accesscontrol/attributes/proto" 32 "github.com/hyperledger/fabric/core/crypto/primitives" 33 ) 34 35 func TestMain(m *testing.M) { 36 if err := primitives.InitSecurityLevel("SHA3", 256); err != nil { 37 fmt.Printf("Failed setting security level: %v", err) 38 } 39 40 ret := m.Run() 41 os.Exit(ret) 42 } 43 44 func TestEncryptDecryptAttributeValuePK0(t *testing.T) { 45 expected := "ACompany" 46 47 preK0 := []byte{ 48 91, 206, 163, 104, 247, 74, 149, 209, 91, 137, 215, 236, 49 84, 135, 9, 70, 160, 138, 89, 163, 240, 223, 83, 164, 58, 50 208, 199, 23, 221, 123, 53, 220, 15, 41, 28, 111, 166, 51 28, 29, 187, 97, 229, 117, 117, 49, 192, 134, 31, 151} 52 53 encryptedAttribute, err := EncryptAttributeValuePK0(preK0, "company", []byte(expected)) 54 if err != nil { 55 t.Error(err) 56 } 57 58 attributeKey := getAttributeKey(preK0, "company") 59 60 attribute, err := DecryptAttributeValue(attributeKey, encryptedAttribute) 61 if err != nil { 62 t.Error(err) 63 } 64 65 if string(attribute) != expected { 66 t.Errorf("Failed decrypting attribute. Expected: %v, Actual: %v", expected, attribute) 67 } 68 } 69 70 func TestGetKAndValueForAttribute(t *testing.T) { 71 expected := "Software Engineer" 72 73 tcert, prek0, err := loadTCertAndPreK0() 74 if err != nil { 75 t.Error(err) 76 } 77 78 _, attribute, err := getKAndValueForAttribute("position", prek0, tcert) 79 if err != nil { 80 t.Error(err) 81 } 82 83 if string(attribute) != expected { 84 t.Errorf("Failed retrieving attribute value from TCert. Expected: %v, Actual: %v", expected, string(attribute)) 85 } 86 } 87 88 func TestGetKAndValueForAttribute_MissingAttribute(t *testing.T) { 89 tcert, prek0, err := loadTCertAndPreK0() 90 if err != nil { 91 t.Error(err) 92 } 93 94 _, _, err = getKAndValueForAttribute("business_unit", prek0, tcert) 95 if err == nil { 96 t.Errorf("Trying to read an attribute that is not part of the TCert should produce an error") 97 } 98 } 99 100 func TestGetValueForAttribute(t *testing.T) { 101 expected := "Software Engineer" 102 103 tcert, prek0, err := loadTCertAndPreK0() 104 if err != nil { 105 t.Error(err) 106 } 107 108 value, err := GetValueForAttribute("position", prek0, tcert) 109 if err != nil { 110 t.Error(err) 111 } 112 113 if string(value) != expected { 114 t.Errorf("Failed retrieving attribute value from TCert. Expected: %v, Actual: %v", expected, string(value)) 115 } 116 } 117 118 func TestGetValueForAttribute_MissingAttribute(t *testing.T) { 119 tcert, prek0, err := loadTCertAndPreK0() 120 if err != nil { 121 t.Error(err) 122 } 123 124 _, err = GetValueForAttribute("business_unit", prek0, tcert) 125 if err == nil { 126 t.Errorf("Trying to read an attribute that is not part of the TCert should produce an error") 127 } 128 } 129 130 func TestGetKForAttribute(t *testing.T) { 131 expected := "Software Engineer" 132 133 tcert, prek0, err := loadTCertAndPreK0() 134 if err != nil { 135 t.Error(err) 136 } 137 138 key, err := GetKForAttribute("position", prek0, tcert) 139 if err != nil { 140 t.Error(err) 141 } 142 143 encryptedValue, err := EncryptAttributeValuePK0(prek0, "position", []byte(expected)) 144 if err != nil { 145 t.Error(err) 146 } 147 148 decryptedValue, err := DecryptAttributeValue(key, encryptedValue) 149 if err != nil { 150 t.Error(err) 151 } 152 153 if string(decryptedValue) != expected { 154 t.Errorf("Failed decrypting attribute used calculated key. Expected: %v, Actual: %v", expected, string(decryptedValue)) 155 } 156 } 157 158 func TestGetKForAttribute_MissingAttribute(t *testing.T) { 159 tcert, prek0, err := loadTCertAndPreK0() 160 if err != nil { 161 t.Error(err) 162 } 163 164 _, err = GetKForAttribute("business_unit", prek0, tcert) 165 if err == nil { 166 t.Errorf("Trying to get a key for an attribute that is not part of the TCert should produce an error") 167 } 168 } 169 170 func TestParseEmptyAttributesHeader(t *testing.T) { 171 _, err := ParseAttributesHeader("") 172 if err == nil { 173 t.Error("Empty header should produce a parsing error") 174 } 175 } 176 177 func TestParseAttributesHeader_NotNumberPosition(t *testing.T) { 178 _, err := ParseAttributesHeader(headerPrefix + "position->a#") 179 if err == nil { 180 t.Error("Not number position in the header should produce a parsing error") 181 } 182 } 183 184 func TestBuildAndParseAttributesHeader(t *testing.T) { 185 attributes := make(map[string]int) 186 attributes["company"] = 1 187 attributes["position"] = 2 188 189 headerRaw, err := BuildAttributesHeader(attributes) 190 if err != nil { 191 t.Error(err) 192 } 193 header := string(headerRaw[:]) 194 195 components, err := ParseAttributesHeader(header) 196 if err != nil { 197 t.Error(err) 198 } 199 200 if len(components) != 2 { 201 t.Errorf("Error parsing header. Expecting two entries in header, found %v instead", len(components)) 202 } 203 204 if components["company"] != 1 { 205 t.Errorf("Error parsing header. Expected %v with value %v, found %v instead", "company", 1, components["company"]) 206 } 207 208 if components["position"] != 2 { 209 t.Errorf("Error parsing header. Expected %v with value %v, found %v instead", "position", 2, components["position"]) 210 } 211 } 212 213 func TestReadAttributeHeader(t *testing.T) { 214 tcert, prek0, err := loadTCertAndPreK0() 215 if err != nil { 216 t.Error(err) 217 } 218 219 headerKey := getAttributeKey(prek0, HeaderAttributeName) 220 221 header, encrypted, err := ReadAttributeHeader(tcert, headerKey) 222 223 if err != nil { 224 t.Error(err) 225 } 226 227 if !encrypted { 228 t.Errorf("Error parsing header. Expecting encrypted header.") 229 } 230 231 if len(header) != 1 { 232 t.Errorf("Error parsing header. Expecting %v entries in header, found %v instead", 1, len(header)) 233 } 234 235 if header["position"] != 1 { 236 t.Errorf("Error parsing header. Expected %v with value %v, found %v instead", "position", 1, header["position"]) 237 } 238 } 239 240 func TestReadAttributeHeader_WithoutHeaderKey(t *testing.T) { 241 tcert, _, err := loadTCertAndPreK0() 242 if err != nil { 243 t.Error(err) 244 } 245 246 _, _, err = ReadAttributeHeader(tcert, nil) 247 248 if err == nil { 249 t.Error(err) 250 } 251 } 252 253 func TestReadAttributeHeader_InvalidHeaderKey(t *testing.T) { 254 tcert, prek0, err := loadTCertAndPreK0() 255 if err != nil { 256 t.Error(err) 257 } 258 259 headerKey := getAttributeKey(prek0, HeaderAttributeName+"_invalid") 260 261 _, _, err = ReadAttributeHeader(tcert, headerKey) 262 263 if err == nil { 264 t.Error(err) 265 } 266 } 267 268 func TestReadTCertAttributeByPosition(t *testing.T) { 269 expected := "Software Engineer" 270 271 tcert, prek0, err := loadTCertAndPreK0() 272 if err != nil { 273 t.Error(err) 274 } 275 276 encryptedAttribute, err := ReadTCertAttributeByPosition(tcert, 1) 277 278 if err != nil { 279 t.Error(err) 280 } 281 282 attributeKey := getAttributeKey(prek0, "position") 283 284 attribute, err := DecryptAttributeValue(attributeKey, encryptedAttribute) 285 286 if err != nil { 287 t.Error(err) 288 } 289 290 if string(attribute) != expected { 291 t.Errorf("Failed retrieving attribute value from TCert. Expected: %v, Actual: %v", expected, string(attribute)) 292 } 293 } 294 295 func TestGetAttributesMetadata(t *testing.T) { 296 metadata := []byte{255, 255, 255, 255} 297 entries := make([]*pb.AttributesMetadataEntry, 1) 298 var entry pb.AttributesMetadataEntry 299 entry.AttributeName = "position" 300 entry.AttributeKey = []byte{0, 0, 0, 0} 301 entries[0] = &entry 302 attributesMetadata := pb.AttributesMetadata{Metadata: metadata, Entries: entries} 303 raw, err := proto.Marshal(&attributesMetadata) 304 if err != nil { 305 t.Error(err) 306 } 307 resultMetadata, err := GetAttributesMetadata(raw) 308 if err != nil { 309 t.Error(err) 310 } 311 if bytes.Compare(resultMetadata.Metadata, attributesMetadata.Metadata) != 0 { 312 t.Fatalf("Invalid metadata expected %v result %v", attributesMetadata.Metadata, resultMetadata.Metadata) 313 } 314 if resultMetadata.Entries[0].AttributeName != attributesMetadata.Entries[0].AttributeName { 315 t.Fatalf("Invalid first entry attribute name expected %v result %v", attributesMetadata.Entries[0].AttributeName, resultMetadata.Entries[0].AttributeName) 316 } 317 if bytes.Compare(resultMetadata.Entries[0].AttributeKey, attributesMetadata.Entries[0].AttributeKey) != 0 { 318 t.Fatalf("Invalid first entry attribute key expected %v result %v", attributesMetadata.Entries[0].AttributeKey, resultMetadata.Entries[0].AttributeKey) 319 } 320 } 321 322 func TestReadTCertAttributeByPosition_InvalidPositions(t *testing.T) { 323 tcert, _, err := loadTCertAndPreK0() 324 if err != nil { 325 t.Error(err) 326 } 327 328 _, err = ReadTCertAttributeByPosition(tcert, 2) 329 330 if err == nil { 331 t.Error("Test should have failed since there is no attribute in the position 2 of the TCert") 332 } 333 334 _, err = ReadTCertAttributeByPosition(tcert, -2) 335 336 if err == nil { 337 t.Error("Test should have failed since attribute positions should be positive integer values") 338 } 339 } 340 341 func TestCreateAttributesMetadataObjectFromCert(t *testing.T) { 342 tcert, preK0, err := loadTCertAndPreK0() 343 if err != nil { 344 t.Error(err) 345 } 346 347 metadata := []byte{255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255} 348 attributeKeys := []string{"position"} 349 metadataObj := CreateAttributesMetadataObjectFromCert(tcert, metadata, preK0, attributeKeys) 350 if bytes.Compare(metadataObj.Metadata, metadata) != 0 { 351 t.Errorf("Invalid metadata result %v but expected %v", metadataObj.Metadata, metadata) 352 } 353 354 entries := metadataObj.GetEntries() 355 if len(entries) != 2 { 356 t.Errorf("Invalid entries in metadata result %v but expected %v", len(entries), 3) 357 } 358 359 firstEntry := entries[0] 360 if firstEntry.AttributeName != "position" { 361 t.Errorf("Invalid first attribute name, this has to be %v but is %v", "position", firstEntry.AttributeName) 362 } 363 firstKey, err := GetKForAttribute("position", preK0, tcert) 364 if err != nil { 365 t.Error(err) 366 } 367 368 if bytes.Compare(firstKey, firstEntry.AttributeKey) != 0 { 369 t.Errorf("Invalid K for first attribute expected %v but returned %v", firstKey, firstEntry.AttributeKey) 370 } 371 } 372 373 func TestCreateAttributesMetadata(t *testing.T) { 374 tcert, preK0, err := loadTCertAndPreK0() 375 376 if err != nil { 377 t.Error(err) 378 } 379 tcertRaw := tcert.Raw 380 metadata := []byte{255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255} 381 attributeKeys := []string{"position"} 382 metadataObjRaw, err := CreateAttributesMetadata(tcertRaw, metadata, preK0, attributeKeys) 383 if err != nil { 384 t.Error(err) 385 } 386 387 var metadataObj pb.AttributesMetadata 388 err = proto.Unmarshal(metadataObjRaw, &metadataObj) 389 if err != nil { 390 t.Error(err) 391 } 392 393 if bytes.Compare(metadataObj.Metadata, metadata) != 0 { 394 t.Errorf("Invalid metadata result %v but expected %v", metadataObj.Metadata, metadata) 395 } 396 397 entries := metadataObj.GetEntries() 398 if len(entries) != 2 { 399 t.Errorf("Invalid entries in metadata result %v but expected %v", len(entries), 3) 400 } 401 402 firstEntry := entries[0] 403 if firstEntry.AttributeName != "position" { 404 t.Errorf("Invalid first attribute name, this has to be %v but is %v", "position", firstEntry.AttributeName) 405 } 406 firstKey, err := GetKForAttribute("position", preK0, tcert) 407 if err != nil { 408 t.Error(err) 409 } 410 411 if bytes.Compare(firstKey, firstEntry.AttributeKey) != 0 { 412 t.Errorf("Invalid K for first attribute expected %v but returned %v", firstKey, firstEntry.AttributeKey) 413 } 414 } 415 416 func TestCreateAttributesMetadata_AttributeNotFound(t *testing.T) { 417 tcert, preK0, err := loadTCertAndPreK0() 418 419 if err != nil { 420 t.Error(err) 421 } 422 tcertRaw := tcert.Raw 423 metadata := []byte{255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255} 424 attributeKeys := []string{"company"} 425 metadataObjRaw, err := CreateAttributesMetadata(tcertRaw, metadata, preK0, attributeKeys) 426 if err != nil { 427 t.Error(err) 428 } 429 430 var metadataObj pb.AttributesMetadata 431 err = proto.Unmarshal(metadataObjRaw, &metadataObj) 432 if err != nil { 433 t.Error(err) 434 } 435 if bytes.Compare(metadataObj.Metadata, metadata) != 0 { 436 t.Errorf("Invalid metadata result %v but expected %v", metadataObj.Metadata, metadata) 437 } 438 439 entries := metadataObj.GetEntries() 440 if len(entries) != 2 { 441 t.Errorf("Invalid entries in metadata result %v but expected %v", len(entries), 3) 442 } 443 444 firstEntry := entries[0] 445 if firstEntry.AttributeName != "company" { 446 t.Errorf("Invalid first attribute name, this has to be %v but is %v", "position", firstEntry.AttributeName) 447 } 448 _, err = GetKForAttribute("company", preK0, tcert) 449 if err == nil { 450 t.Fatalf("Test should faild because company is not included within the TCert.") 451 } 452 } 453 454 func TestCreateAttributesMetadataObjectFromCert_AttributeNotFound(t *testing.T) { 455 tcert, preK0, err := loadTCertAndPreK0() 456 if err != nil { 457 t.Error(err) 458 } 459 460 metadata := []byte{255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255} 461 attributeKeys := []string{"company"} 462 metadataObj := CreateAttributesMetadataObjectFromCert(tcert, metadata, preK0, attributeKeys) 463 if bytes.Compare(metadataObj.Metadata, metadata) != 0 { 464 t.Errorf("Invalid metadata result %v but expected %v", metadataObj.Metadata, metadata) 465 } 466 467 entries := metadataObj.GetEntries() 468 if len(entries) != 2 { 469 t.Errorf("Invalid entries in metadata result %v but expected %v", len(entries), 3) 470 } 471 472 firstEntry := entries[0] 473 if firstEntry.AttributeName != "company" { 474 t.Errorf("Invalid first attribute name, this has to be %v but is %v", "position", firstEntry.AttributeName) 475 } 476 _, err = GetKForAttribute("company", preK0, tcert) 477 if err == nil { 478 t.Fatalf("Test should faild because company is not included within the TCert.") 479 } 480 } 481 482 func TestBuildAttributesHeader(t *testing.T) { 483 attributes := make(map[string]int) 484 attributes["company"] = 0 485 attributes["position"] = 1 486 attributes["country"] = 2 487 result, err := BuildAttributesHeader(attributes) 488 if err != nil { 489 t.Error(err) 490 } 491 492 resultStr := string(result) 493 494 if !strings.HasPrefix(resultStr, headerPrefix) { 495 t.Fatalf("Invalid header prefix expected %v result %v", headerPrefix, resultStr) 496 } 497 498 if !strings.Contains(resultStr, "company->0#") { 499 t.Fatalf("Invalid header shoud include '%v'", "company->0#") 500 } 501 502 if !strings.Contains(resultStr, "position->1#") { 503 t.Fatalf("Invalid header shoud include '%v'", "position->1#") 504 } 505 506 if !strings.Contains(resultStr, "country->2#") { 507 t.Fatalf("Invalid header shoud include '%v'", "country->2#") 508 } 509 } 510 511 func TestBuildAttributesHeader_DuplicatedPosition(t *testing.T) { 512 attributes := make(map[string]int) 513 attributes["company"] = 0 514 attributes["position"] = 0 515 attributes["country"] = 1 516 _, err := BuildAttributesHeader(attributes) 517 if err == nil { 518 t.Fatalf("Error this tests should fail because header has two attributes with the same position") 519 } 520 } 521 522 func loadTCertAndPreK0() (*x509.Certificate, []byte, error) { 523 preKey0, err := ioutil.ReadFile("./test_resources/prek0.dump") 524 if err != nil { 525 return nil, nil, err 526 } 527 528 if err != nil { 529 return nil, nil, err 530 } 531 532 tcertRaw, err := ioutil.ReadFile("./test_resources/tcert.dump") 533 if err != nil { 534 return nil, nil, err 535 } 536 537 tcertDecoded, _ := pem.Decode(tcertRaw) 538 539 tcert, err := x509.ParseCertificate(tcertDecoded.Bytes) 540 if err != nil { 541 return nil, nil, err 542 } 543 544 return tcert, preKey0, nil 545 }