package Ġorg . be ck n . one . sandbox . b ap . protocol . shared . security Ċ Ċ import Ġcom . fasterxml . jackson . databind . ObjectMapper Ċ import Ġcom . github . tom ake hur st . wire mock . client . Wire Mock Ċ import Ġio . kot est . core . spec . style . Describe Spec Ċ import Ġio . kot est . matchers . null s . be Null Ċ import Ġio . kot est . matchers . shouldBe Ċ import Ġio . kot est . matchers . should Not Ċ import Ġorg . be ck n . one . sandbox . b ap . common . factories . Mock Network Ċ import Ġorg . be ck n . one . sandbox . b ap . message . factories .* Ċ import Ġorg . be ck n . protocol . schemas .* Ċ import Ġorg . springframework . beans . factory . annotation . Autowired Ċ import Ġorg . springframework . boot . test . context . SpringBootTest Ċ import Ġorg . springframework . boot . test . web . client . Test Rest Template Ċ import Ġorg . springframework . boot . web . server . Local Server Port Ċ import Ġorg . springframework . http . Http Entity Ċ import Ġorg . springframework . http . HttpHeaders Ċ import Ġorg . springframework . http . MediaType Ċ import Ġorg . springframework . test . context . Active Profiles Ċ import Ġjava . time . Instant Ċ Ċ @ SpringBootTest ( ĊĠ Ġweb Environment Ġ= ĠSpring Boot Test . Web Environment . RANDOM _ PORT , ĊĠ Ġproperties Ġ= Ġ[" be ck n . security . enabled = true "] Ċ ) Ċ @ Active Profiles ( value Ġ= Ġ[" test "]) Ċ class ĠSignature Verification Interceptor Spec ( ĊĠ Ġ@ Local Server Port Ġport : ĠInt , ĊĠ Ġ@ Autowired Ġrest Template : ĠTest Rest Template , ĊĠ Ġ@ Autowired Ġmapper : ĠObjectMapper Ċ ) Ġ: ĠDescribe Spec () Ġ{ ĊĊĠ Ġprivate Ġval Ġb 6 4 PrivateKey Ġ= Ġ" 8 j 0 Men by 6 + O 4 k Uk E 2 y DJ w 4 u 0 pq Wm Ad lf ts RO X lb K HV GH lb 0 U 6 bk Lc 8 5 7 v BB KH CL 5 TD s Lx sw 7 mq J FI 0 cy C 7 / a 8 A ==" ĊĠ Ġprivate Ġval Ġerror Body Ġ= Ġ""" ĊĠĠĠ Ġ{" message ":{" ack ":{" status ":" N ACK "}} } ĊĠĠĠ Ġ""" . trim Indent () ĊĊĠ Ġval Ġregistry Api Ġ= ĠMock Network . registry B pp Lookup Api ĊĊĠ Ġinit Ġ{ ĊĠĠĠ Ġregistry Api . stub For ( ĊĠĠĠĠĠ ĠWire Mock . post ("/ lookup ") ĊĠĠĠĠĠĠĠ Ġ. willReturn ( Wire Mock . server Error ()) ĊĠĠĠ Ġ) ĊĠĠĠ Ġregistry Api . start () ĊĊĠĠĠ Ġfun Ġcreate Request ( ĊĠĠĠĠĠ Ġrequest Body : ĠString , ĊĠĠĠĠĠ Ġauth Header Name : ĠString ? Ġ= Ġnull , ĊĠĠĠĠĠ Ġauth String : ĠString ? Ġ= Ġnull ĊĠĠĠ Ġ): ĠHttp Entity < String > Ġ{ ĊĠĠĠĠĠ Ġval Ġheaders Ġ= ĠHttp Headers () ĊĠĠĠĠĠ Ġheaders . contentType Ġ= ĠMediaType . APPLICATION _ JSON ĊĠĠĠĠĠ Ġval Ġh Name Ġ= Ġauth Header Name Ġ?: Ġreturn ĠHttp Entity ( request Body , Ġheaders ) ĊĠĠĠĠĠ Ġval Ġh Value Ġ= Ġauth String Ġ?: Ġreturn ĠHttp Entity ( request Body , Ġheaders ) ĊĠĠĠĠĠ Ġheaders . set ( h Name , Ġh Value ) ĊĠĠĠĠĠ Ġreturn ĠHttp Entity ( request Body , Ġheaders ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġfun Ġsign Request ( request Body : ĠString ): ĠAuthorization Ġ{ ĊĠĠĠĠĠ Ġval Ġcreated Ġ= ĠInstant . now (). to Epoch Milli () Ġ/ Ġ 1 0 0 0 ĊĠĠĠĠĠ Ġval Ġexpires Ġ= ĠInstant . now (). plus Seconds ( 1 0 0 0 0 ). to Epoch Milli () Ġ/ Ġ 1 0 0 0 ĊĠĠĠĠĠ Ġreturn ĠAuthorization ( ĊĠĠĠĠĠĠĠ Ġkey Id Ġ= Ġ" MOCK _ SUB _ ID | key 1 | xed 2 5 5 1 9 ", ĊĠĠĠĠĠĠĠ Ġcreated Ġ= Ġcreated , ĊĠĠĠĠĠĠĠ Ġexpires Ġ= Ġexpires , ĊĠĠĠĠĠĠĠ Ġsignature Ġ= ĠCrypt ic . sign ( b 6 4 PrivateKey , Ġrequest Body , Ġcreated , Ġexpires ) ĊĠĠĠĠĠ Ġ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġdescribe (" Signature Verification Interceptor Ġfor Ġon Ġsearch Ġcallback ") Ġ{ ĊĠĠĠĠĠ Ġval Ġschema Search Response Ġ= ĠProtocol On Search ( ĊĠĠĠĠĠĠĠ Ġcontext Ġ= ĠProtocol Context Factory . fixed , ĊĠĠĠĠĠĠĠ Ġmessage Ġ= ĠProtocol On Search Message ( Protocol Catalog Factory . create ( 2 )) ĊĠĠĠĠĠ Ġ) ĊĠĠĠĠĠ Ġval Ġrequest Body : ĠString Ġ= Ġmapper . writeValue AsString ( schema Search Response ) ĊĊĠĠĠĠĠ Ġcontext (" when ĠAuthorization Ġheader Ġis Ġmissing Ġin Ġsearch Ġrequest ") Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġresponse Entity Ġ= Ġrest Template ĊĠĠĠĠĠĠĠĠĠ Ġ. post For Entity (" http :// localhost :$ port / protocol / v 1 / on _ search ", Ġcreate Request ( request Body ), ĠString :: class . java ) ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġreturn Ġ 4 0 1 ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . statusCode . value () ĠshouldBe Ġ 4 0 1 ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġset ĠW WW - Authenticate Ġheader ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . headers [" WW W - Authenticate "] Ġshould Not Ġbe Null () ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġsend Ġn ack Ġin Ġbody ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . body !! ĠshouldBe Ġerror Body ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠ Ġcontext (" when Ġrequest Ġhas Ġvalid ĠAuthorization Ġheader ") Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġauthorization Ġ= Ġsign Request ( request Body ) ĊĠĠĠĠĠĠĠ Ġval Ġrequest Ġ= Ġcreate Request ( request Body , Ġ" Authorization ", Ġauthorization . header String ) ĊĠĠĠĠĠĠĠ Ġval Ġresponse Entity Ġ= Ġrest Template ĊĠĠĠĠĠĠĠĠĠ Ġ. post For Entity (" http :// localhost :$ port / protocol / v 1 / on _ search ", Ġrequest , ĠString :: class . java ) ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġforward Ġto Ġcontroller Ġand Ġresponse Ġshould Ġbe Ġ 2 0 0 ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . statusCode . value () ĠshouldBe Ġ 2 0 0 ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġdescribe (" Signature Verification Interceptor Ġfor Ġselect Ġcallback ĠAPIs ") Ġ{ ĊĠĠĠĠĠ Ġval Ġschema Select Response Ġ= ĠProtocol On Select ( ĊĠĠĠĠĠĠĠ Ġcontext Ġ= ĠProtocol Context Factory . fixed , ĊĠĠĠĠĠĠĠ Ġmessage Ġ= ĠProtocol On Select Message ( Protocol On Select Message Selected Factory . create ( 1 , Ġ 2 )) ĊĠĠĠĠĠ Ġ) ĊĠĠĠĠĠ Ġval Ġrequest Body : ĠString Ġ= Ġmapper . writeValue AsString ( schema Select Response ) ĊĊĠĠĠĠĠ Ġcontext (" when ĠAuthorization Ġheader Ġis Ġmissing Ġin Ġsearch Ġrequest ") Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġresponse Entity Ġ= Ġrest Template . post For Entity ( ĊĠĠĠĠĠĠĠĠĠ Ġ" http :// localhost :$ port / protocol / v 1 / on _ select ", ĊĠĠĠĠĠĠĠĠĠ Ġcreate Request ( request Body ), ĊĠĠĠĠĠĠĠĠĠ ĠString :: class . java ĊĠĠĠĠĠĠĠ Ġ) ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġreturn Ġ 4 0 1 ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . statusCode . value () ĠshouldBe Ġ 4 0 1 ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġset ĠW WW - Authenticate Ġheader ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . headers [" WW W - Authenticate "] Ġshould Not Ġbe Null () ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġsend Ġn ack Ġin Ġbody ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . body !! ĠshouldBe Ġerror Body ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠ Ġcontext (" when Ġrequest Ġhas Ġvalid ĠAuthorization Ġheader ") Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġauthorization Ġ= Ġsign Request ( request Body ) ĊĠĠĠĠĠĠĠ Ġval Ġrequest Ġ= Ġcreate Request ( request Body , Ġ" Authorization ", Ġauthorization . header String ) ĊĠĠĠĠĠĠĠ Ġval Ġresponse Entity Ġ= Ġrest Template ĊĠĠĠĠĠĠĠĠĠ Ġ. post For Entity (" http :// localhost :$ port / protocol / v 1 / on _ select ", Ġrequest , ĠString :: class . java ) ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġforward Ġto Ġcontroller Ġand Ġresponse Ġshould Ġbe Ġ 2 0 0 ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . statusCode . value () ĠshouldBe Ġ 2 0 0 ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠ Ġ} ĊĊĊĠĠĠ Ġ} ĊĊĠĠĠ Ġdescribe (" Signature Verification Interceptor Ġfor Ġinit Ġcallback ĠAPIs ") Ġ{ ĊĠĠĠĠĠ Ġval Ġschema Init Response Ġ= ĠProtocol OnInit ( ĊĠĠĠĠĠĠĠ Ġcontext Ġ= ĠProtocol Context Factory . fixed , ĊĠĠĠĠĠĠĠ Ġmessage Ġ= ĠProtocol OnInit Message ( Protocol OnInit Message Initialized Factory . create ( 1 , Ġ 2 )) ĊĠĠĠĠĠ Ġ) ĊĠĠĠĠĠ Ġval Ġrequest Body : ĠString Ġ= Ġmapper . writeValue AsString ( schema Init Response ) ĊĊĠĠĠĠĠ Ġcontext (" when ĠAuthorization Ġheader Ġis Ġmissing Ġin Ġsearch Ġrequest ") Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġresponse Entity Ġ= Ġrest Template . post For Entity ( ĊĠĠĠĠĠĠĠĠĠ Ġ" http :// localhost :$ port / protocol / v 1 / on _ init ", Ġcreate Request ( request Body ), ĠString :: class . java ĊĠĠĠĠĠĠĠ Ġ) ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġreturn Ġ 4 0 1 ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . statusCode . value () ĠshouldBe Ġ 4 0 1 ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġset ĠW WW - Authenticate Ġheader ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . headers [" WW W - Authenticate "] Ġshould Not Ġbe Null () ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġsend Ġn ack Ġin Ġbody ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . body !! ĠshouldBe Ġerror Body ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠ Ġcontext (" when Ġrequest Ġhas Ġvalid ĠAuthorization Ġheader ") Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġauthorization Ġ= Ġsign Request ( request Body ) ĊĠĠĠĠĠĠĠ Ġval Ġrequest Ġ= Ġcreate Request ( request Body , Ġ" Authorization ", Ġauthorization . header String ) ĊĠĠĠĠĠĠĠ Ġval Ġresponse Entity Ġ= Ġrest Template ĊĠĠĠĠĠĠĠĠĠ Ġ. post For Entity (" http :// localhost :$ port / protocol / v 1 / on _ init ", Ġrequest , ĠString :: class . java ) ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġforward Ġto Ġcontroller Ġand Ġresponse Ġshould Ġbe Ġ 2 0 0 ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . statusCode . value () ĠshouldBe Ġ 2 0 0 ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġdescribe (" Signature Verification Interceptor Ġfor Ġconfirm Ġcallback ĠAPIs ") Ġ{ ĊĠĠĠĠĠ Ġval Ġschema Confirm Response Ġ= ĠProtocol On Confirm ( ĊĠĠĠĠĠĠĠ Ġcontext Ġ= ĠProtocol Context Factory . fixed , ĊĠĠĠĠĠĠĠ Ġmessage Ġ= ĠProtocol On Confirm Message ( Protocol Order Factory . create ( 1 )) ĊĠĠĠĠĠ Ġ) ĊĠĠĠĠĠ Ġval Ġrequest Body : ĠString Ġ= Ġmapper . writeValue AsString ( schema Confirm Response ) ĊĊĠĠĠĠĠ Ġcontext (" when ĠAuthorization Ġheader Ġis Ġmissing Ġin Ġsearch Ġrequest ") Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġresponse Entity Ġ= Ġrest Template . post For Entity ( ĊĠĠĠĠĠĠĠĠĠ Ġ" http :// localhost :$ port / protocol / v 1 / on _ confirm ", Ġcreate Request ( request Body ), ĠString :: class . java ĊĠĠĠĠĠĠĠ Ġ) ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġreturn Ġ 4 0 1 ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . statusCode . value () ĠshouldBe Ġ 4 0 1 ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġset ĠW WW - Authenticate Ġheader ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . headers [" WW W - Authenticate "] Ġshould Not Ġbe Null () ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġsend Ġn ack Ġin Ġbody ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . body !! ĠshouldBe Ġerror Body ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠ Ġcontext (" when Ġrequest Ġhas Ġvalid ĠAuthorization Ġheader ") Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġauthorization Ġ= Ġsign Request ( request Body ) ĊĠĠĠĠĠĠĠ Ġval Ġrequest Ġ= Ġcreate Request ( request Body , Ġ" Authorization ", Ġauthorization . header String ) ĊĠĠĠĠĠĠĠ Ġval Ġresponse Entity Ġ= Ġrest Template ĊĠĠĠĠĠĠĠĠĠ Ġ. post For Entity (" http :// localhost :$ port / protocol / v 1 / on _ confirm ", Ġrequest , ĠString :: class . java ) ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġforward Ġto Ġcontroller Ġand Ġresponse Ġshould Ġbe Ġ 2 0 0 ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . statusCode . value () ĠshouldBe Ġ 2 0 0 ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġdescribe (" Signature Verification Interceptor Ġfor Ġtrack Ġcallback ĠAPIs ") Ġ{ ĊĠĠĠĠĠ Ġval Ġschema Track Response Ġ= ĠProtocol On Track ( ĊĠĠĠĠĠĠĠ Ġcontext Ġ= ĠProtocol Context Factory . fixed , ĊĠĠĠĠĠĠĠ Ġmessage Ġ= ĠProtocol On Track Message ( Protocol On Track Message Tracking Factory . create ( 1 )) ĊĠĠĠĠĠ Ġ) ĊĠĠĠĠĠ Ġval Ġrequest Body : ĠString Ġ= Ġmapper . writeValue AsString ( schema Track Response ) ĊĊĠĠĠĠĠ Ġcontext (" when ĠAuthorization Ġheader Ġis Ġmissing Ġin Ġsearch Ġrequest ") Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġresponse Entity Ġ= Ġrest Template . post For Entity ( ĊĠĠĠĠĠĠĠĠĠ Ġ" http :// localhost :$ port / protocol / v 1 / on _ track ", Ġcreate Request ( request Body ), ĠString :: class . java ĊĠĠĠĠĠĠĠ Ġ) ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġreturn Ġ 4 0 1 ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . statusCode . value () ĠshouldBe Ġ 4 0 1 ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġset ĠW WW - Authenticate Ġheader ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . headers [" WW W - Authenticate "] Ġshould Not Ġbe Null () ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġsend Ġn ack Ġin Ġbody ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . body !! ĠshouldBe Ġerror Body ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠ Ġcontext (" when Ġrequest Ġhas Ġvalid ĠAuthorization Ġheader ") Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġauthorization Ġ= Ġsign Request ( request Body ) ĊĠĠĠĠĠĠĠ Ġval Ġrequest Ġ= Ġcreate Request ( request Body , Ġ" Authorization ", Ġauthorization . header String ) ĊĠĠĠĠĠĠĠ Ġval Ġresponse Entity Ġ= Ġrest Template ĊĠĠĠĠĠĠĠĠĠ Ġ. post For Entity (" http :// localhost :$ port / protocol / v 1 / on _ track ", Ġrequest , ĠString :: class . java ) ĊĊĠĠĠĠĠĠĠ Ġit (" should Ġforward Ġto Ġcontroller Ġand Ġresponse Ġshould Ġbe Ġ 2 0 0 ") Ġ{ ĊĠĠĠĠĠĠĠĠĠ Ġresponse Entity . statusCode . value () ĠshouldBe Ġ 2 0 0 ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠ Ġ} ĊĠĠĠ Ġ} ĊĠ Ġ} Ċ Ċ } Ċ