@@ -53,7 +53,11 @@ func generateSignature(name string, signer Signer, input string) (string, error)
5353 if err != nil {
5454 return "" , err
5555 }
56- return fmt .Sprintf ("%s=:%s:" , name , base64 .StdEncoding .EncodeToString (raw )), nil
56+ return fmt .Sprintf ("%s=%s" , name , encodeBytes (raw )), nil
57+ }
58+
59+ func encodeBytes (raw []byte ) string {
60+ return ":" + base64 .StdEncoding .EncodeToString (raw ) + ":"
5761}
5862
5963func generateSignatureInput (message parsedMessage , fields Fields , params string ) (string , error ) {
@@ -110,6 +114,9 @@ func SignRequest(signatureName string, signer Signer, req *http.Request) (signat
110114 if signatureName == "" {
111115 return "" , "" , fmt .Errorf ("empty signature name" )
112116 }
117+ if signer .config .requestResponse != nil {
118+ return "" , "" , fmt .Errorf ("use request-response only to sign responses" )
119+ }
113120 parsedMessage , err := parseRequest (req )
114121 if err != nil {
115122 return "" , "" , err
@@ -131,15 +138,22 @@ func SignResponse(signatureName string, signer Signer, res *http.Response) (sign
131138 if err != nil {
132139 return "" , "" , err
133140 }
134- addPseudoHeaders (parsedMessage , * signer .config )
135- return signMessage (* signer .config , signatureName , signer , * parsedMessage , signer . fields )
141+ extendedFields := addPseudoHeaders (parsedMessage , signer .config . requestResponse , signer . fields )
142+ return signMessage (* signer .config , signatureName , signer , * parsedMessage , extendedFields )
136143}
137144
138- func addPseudoHeaders (message * parsedMessage , config SignConfig ) {
139- if config .requestResponse .name != "" {
140- message .components [* fromHeaderName ("@request-response" )] = []string {config .requestResponse .signature }
141- // TODO and what about the name? (request-response)
145+ // Handle the special header-like @request-response
146+ func addPseudoHeaders (message * parsedMessage , rr * requestResponse , fields Fields ) Fields {
147+ if rr != nil {
148+ rrfield := field {
149+ name : "@request-response" ,
150+ flagName : "key" ,
151+ flagValue : rr .name ,
152+ }
153+ message .components [rrfield ] = []string {rr .signature }
154+ return append (fields , rrfield )
142155 }
156+ return fields
143157}
144158
145159//
@@ -152,11 +166,14 @@ func VerifyRequest(signatureName string, verifier Verifier, req *http.Request) (
152166 if signatureName == "" {
153167 return fmt .Errorf ("empty signature name" )
154168 }
169+ if verifier .config .requestResponse != nil {
170+ return fmt .Errorf ("use request-response only to verify responses" )
171+ }
155172 parsedMessage , err := parseRequest (req )
156173 if err != nil {
157174 return err
158175 }
159- return verifyMessage (* verifier .c , signatureName , verifier , * parsedMessage , verifier .f )
176+ return verifyMessage (* verifier .config , signatureName , verifier , * parsedMessage , verifier .fields )
160177}
161178
162179// RequestDetails parses a signed request and returns the key ID and optionally the algorithm used in the given signature.
@@ -189,6 +206,31 @@ func ResponseDetails(signatureName string, res *http.Response) (keyID, alg strin
189206 return messageKeyID (signatureName , * parsedMessage )
190207}
191208
209+ // GetRequestSignature returns the base64-encoded signature, parsed from a signed request.
210+ // This is useful for the request-response feature.
211+ func GetRequestSignature (req * http.Request , signatureName string ) (string , error ) {
212+ if req == nil {
213+ return "" , fmt .Errorf ("nil request" )
214+ }
215+ if signatureName == "" {
216+ return "" , fmt .Errorf ("empty signature name" )
217+ }
218+ parsedMessage , err := parseRequest (req )
219+ if err != nil {
220+ return "" , err
221+ }
222+ ws , found := parsedMessage .components [* fromHeaderName ("signature" )]
223+ if ! found {
224+ return "" , fmt .Errorf ("missing \" signature\" header" )
225+ }
226+ sigHeader := ws [0 ]
227+ sigRaw , err := parseWantSignature (sigHeader , signatureName )
228+ if err != nil {
229+ return "" , err
230+ }
231+ return encodeBytes (sigRaw ), nil
232+ }
233+
192234func messageKeyID (signatureName string , parsedMessage parsedMessage ) (keyID , alg string , err error ) {
193235 si , found := parsedMessage .components [* fromHeaderName ("signature-input" )]
194236 if ! found {
@@ -231,7 +273,8 @@ func VerifyResponse(signatureName string, verifier Verifier, res *http.Response)
231273 if err != nil {
232274 return err
233275 }
234- return verifyMessage (* verifier .c , signatureName , verifier , * parsedMessage , verifier .f )
276+ extendedFields := addPseudoHeaders (parsedMessage , verifier .config .requestResponse , verifier .fields )
277+ return verifyMessage (* verifier .config , signatureName , verifier , * parsedMessage , extendedFields )
235278}
236279
237280func verifyMessage (config VerifyConfig , name string , verifier Verifier , message parsedMessage , fields Fields ) error {
0 commit comments