diff --git a/datatrails-common-api/assets/v2/assets/accesspolicy.go b/datatrails-common-api/assets/v2/assets/accesspolicy.go index ea223ee..a4a9e32 100644 --- a/datatrails-common-api/assets/v2/assets/accesspolicy.go +++ b/datatrails-common-api/assets/v2/assets/accesspolicy.go @@ -38,6 +38,31 @@ func (a *AssetResponse) AccessPolicyStringValue(name, defaultValue string) (stri return value, nil } +// IsPubliclyAttested determines if an asset is publicly attested +// if public wallet address is present *anywhere* in the policy +// we assume the asset is public as there is no other way of getting +// public wallet to policy other than setting public: true on an asset +// previous method was to specific and did not work with partial attestation +func (a *AssetResponse) IsPubliclyAttested(publicWallet string) bool { + + for attrs := range a.AccessPolicy { + data, ok := a.AccessPolicy[attrs].GetList() + if !ok { + continue + } + + for _, v := range data { + if vv, ok := v[publicWallet]; ok { + if vv == "wallet" { + return true + } + } + } + } + + return false +} + // IsSharedForWallet determines if the value identified by `attribute` is shared // with the organisation identified by `wallet`. `policyKey` determines the kind // of share: asset attribute or event attribute and whether it is a read share diff --git a/datatrails-common-api/assets/v2/assets/accesspolicy_test.go b/datatrails-common-api/assets/v2/assets/accesspolicy_test.go index 3235c36..75c93a3 100644 --- a/datatrails-common-api/assets/v2/assets/accesspolicy_test.go +++ b/datatrails-common-api/assets/v2/assets/accesspolicy_test.go @@ -398,6 +398,102 @@ func TestAssetResponse_IsSharedForWallet_AssetAttributesMixedWildeReader(t *test } } +// TestAssetResponse_IsPubliclyAttested_AssetAttributesMixedWildeReader +// Covers mixed read cases (wild card present in policy, all shares are read shares) +func TestAssetResponse_IsPubliclyAttested_AssetAttributesMixedWildeReader(t *testing.T) { + + type fields struct { + AccessPolicy map[string]*v2attribute.Attribute + } + type args struct { + policyKey string + wallet string + attribute string + } + + Wallet1 := "0xWALLET1" + Wallet2 := "0xWALLET2" + WalletWild := "0xWILD-WALLET" + + TesseraPub1 := "b64-TESSERAPUB1" + TesseraPub2 := "b64-TESSERAPUB2" + TesseraPubWild := "b64-TESSERAPUB-WILD" + tractor_colour := "tractor_colour" + engine_size := "engine_size" + + twoReadSharedAssetAttributesAndOneWildWallet := map[string]*v2attribute.Attribute{} + + policyAddAssetAttributeReaderOrFailNow( + t, twoReadSharedAssetAttributesAndOneWildWallet, tractor_colour, Wallet1, TesseraPub1) + policyAddAssetAttributeReaderOrFailNow( + t, twoReadSharedAssetAttributesAndOneWildWallet, engine_size, Wallet2, TesseraPub2) + policyAddAssetAttributeReaderOrFailNow( + t, twoReadSharedAssetAttributesAndOneWildWallet, "*", WalletWild, TesseraPubWild) + + tests := []struct { + name string + fields fields + args args + want bool + wantErr bool + }{ + // TODO: Add test cases. + { + name: "Should match wildwallet in policy sharing two asset attributes", + fields: fields{ + AccessPolicy: twoReadSharedAssetAttributesAndOneWildWallet, + }, + args: args{ + wallet: WalletWild, + }, + want: true, + }, + { + name: "Should match wildwallet in policy sharing two asset attributes", + fields: fields{ + AccessPolicy: twoReadSharedAssetAttributesAndOneWildWallet, + }, + args: args{ + wallet: WalletWild, + }, + want: true, + }, + + { + name: "Should match wallet1 in policy sharing two asset attributes", + fields: fields{ + AccessPolicy: twoReadSharedAssetAttributesAndOneWildWallet, + }, + args: args{ + wallet: Wallet1, + }, + want: true, + }, + + { + name: "Should match wallet2 in policy even partial share", + fields: fields{ + AccessPolicy: twoReadSharedAssetAttributesAndOneWildWallet, + }, + args: args{ + wallet: Wallet2, + }, + want: true, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + a := &AssetResponse{ + AccessPolicy: tt.fields.AccessPolicy, + } + got := a.IsPubliclyAttested(tt.args.wallet) + if got != tt.want { + t.Errorf("AssetResponse.IsPubliclyAttested() = %v, want %v", got, tt.want) + } + }) + } +} + func policyAddAssetAttributeReaderOrFailNow( t *testing.T, policy map[string]*v2attribute.Attribute, diff --git a/getproto.sh b/getproto.sh new file mode 100755 index 0000000..9376fc3 --- /dev/null +++ b/getproto.sh @@ -0,0 +1,3 @@ +#!/usr/bin/sh +cd datatrails-common-api/ +echo $(GOCACHE=/tmp/datatrails/go-datatrails-common-api/api go list -f {{.Dir}} $1) \ No newline at end of file diff --git a/taskfiles/Taskfile_apis.yml b/taskfiles/Taskfile_apis.yml index d51175f..4219e1c 100644 --- a/taskfiles/Taskfile_apis.yml +++ b/taskfiles/Taskfile_apis.yml @@ -253,17 +253,15 @@ tasks: # return for this. AND it makes iteratively generating proto changes # across repositories a lot more efficient sh: | - cd datatrails-common-api - echo $(GOCACHE=/tmp/datatrails/go-datatrails-common-api/api go list -f {{"{{"}}.Dir{{"}}"}} google.golang.org/protobuf/cmd/protoc-gen-go) + echo $(./getproto.sh google.golang.org/protobuf/cmd/protoc-gen-go) GRPC_GATEWAY_DIR: sh: | - cd datatrails-common-api - echo $(dirname $(GOCACHE=/tmp/datatrails/go-datatrails-common-api/api go list -f {{"{{"}}.Dir{{"}}"}} github.com/grpc-ecosystem/grpc-gateway/v2/runtime)) + echo $(dirname $(./getproto.sh github.com/grpc-ecosystem/grpc-gateway/v2/runtime)) + ENVOY_VALIDATE: sh: | - cd datatrails-common-api - echo $(GOCACHE=/tmp/datatrails/go-datatrails-common-api/api go list -f {{"{{"}}.Dir{{"}}"}} github.com/envoyproxy/protoc-gen-validate) + echo $(./getproto.sh github.com/envoyproxy/protoc-gen-validate) SELF_INC: .