public HttpRequest sign(HttpRequest request) { // Grab the needed data to build the signature Multimap<String, String> canonicalizedHeadersMap = buildCanonicalizedHeadersMap(request); String canonicalizedHeadersString = buildCanonicalizedHeadersString(canonicalizedHeadersMap); String signedHeaders = buildSignedHeaders(canonicalizedHeadersMap); String date = request.getFirstHeaderOrNull(GlacierHeaders.ALTERNATE_DATE); String dateWithoutTimestamp = formatDateWithoutTimestamp(date); String method = request.getMethod(); String endpoint = request.getEndpoint().getRawPath(); String credentialScope = buildCredentialScope(dateWithoutTimestamp); HashCode hashedPayload = buildHashedPayload(request); // Task 1: Create a Canonical Request For Signature Version 4. HashCode hashedCanonicalRequest = buildHashedCanonicalRequest( method, endpoint, hashedPayload, canonicalizedHeadersString, signedHeaders); // Task 2: Create a String to Sign for Signature Version 4. String stringToSign = createStringToSign(date, credentialScope, hashedCanonicalRequest); // Task 3: Calculate the AWS Signature Version 4. String signature = buildSignature(dateWithoutTimestamp, stringToSign); // Sign the request String authHeader = buildAuthHeader(identity, credentialScope, signedHeaders, signature); request = request.toBuilder().replaceHeader(HttpHeaders.AUTHORIZATION, authHeader).build(); return request; }
@Override public HttpRequest filter(HttpRequest request) throws HttpException { return request .toBuilder() .replaceHeader(AuthHeaders.AUTH_TOKEN, authTokenProvider.get()) .build(); }
private HttpRequest signForTemporaryAccess(HttpRequest request, long timeInSeconds) { // Update the 'DATE' header String dateString = request.getFirstHeaderOrNull(HttpHeaders.DATE); if (dateString == null) { dateString = timeStampProvider.get(); } Date date = dateService.rfc1123DateParse(dateString); String expiration = String.valueOf(TimeUnit.MILLISECONDS.toSeconds(date.getTime()) + timeInSeconds); HttpRequest.Builder<?> builder = request.toBuilder().replaceHeader(HttpHeaders.DATE, expiration); String stringToSign = authSigner.createStringToSign(builder.build()); // We MUST encode the signature because addQueryParam internally _always_ decodes values // and if we don't encode the signature here, the decoding may change the signature. For e.g. // any '+' characters in the signature will be converted to space ' ' on decoding. String signature = authSigner.sign(stringToSign); try { signature = URLEncoder.encode(signature, Charsets.UTF_8.name()); } catch (UnsupportedEncodingException e) { throw new IllegalStateException("Bad encoding on input: " + signature, e); } HttpRequest ret = builder .addQueryParam(HttpHeaders.EXPIRES, expiration) .addQueryParam("AWSAccessKeyId", identity) // Signature MUST be the last parameter because if it isn't, even encoded '+' values in // the // signature will be converted to a space by a subsequent addQueryParameter. // See HttpRequestTest.testAddBase64AndUrlEncodedQueryParams for more details. .addQueryParam(TEMPORARY_SIGNATURE_PARAM, signature) .build(); return ret; }
public HttpRequest filter(HttpRequest input) throws HttpException { HttpRequest request = input.toBuilder().endpoint(input.getEndpoint().toString().replace("%3F", "?")).build(); String contentHash = hashBody(request.getPayload()); Multimap<String, String> headers = ArrayListMultimap.create(); headers.put("X-Ops-Content-Hash", contentHash); String timestamp = timeStampProvider.get(); String toSign = createStringToSign( request.getMethod(), hashPath(request.getEndpoint().getPath()), contentHash, timestamp); headers.put("X-Ops-Userid", creds.get().identity); headers.put("X-Ops-Sign", SIGNING_DESCRIPTION); request = calculateAndReplaceAuthorizationHeaders(request, toSign); headers.put("X-Ops-Timestamp", timestamp); utils.logRequest(signatureLog, request, "<<"); return request.toBuilder().replaceHeaders(headers).build(); }
@VisibleForTesting HttpRequest calculateAndReplaceAuthorizationHeaders(HttpRequest request, String toSign) throws HttpException { String signature = sign(toSign); if (signatureWire.enabled()) signatureWire.input(Strings2.toInputStream(signature)); String[] signatureLines = Iterables.toArray(Splitter.fixedLength(60).split(signature), String.class); Multimap<String, String> headers = ArrayListMultimap.create(); for (int i = 0; i < signatureLines.length; i++) { headers.put("X-Ops-Authorization-" + (i + 1), signatureLines[i]); } return request.toBuilder().replaceHeaders(headers).build(); }
@Override public HttpRequest filter(HttpRequest request) throws HttpException { checkState( request instanceof GeneratedHttpRequest, "request must be an instance of GeneratedHttpRequest"); GeneratedHttpRequest generatedHttpRequest = GeneratedHttpRequest.class.cast(request); TokenRequest tokenRequest = tokenRequestBuilder.apply(generatedHttpRequest); Token token = tokenFetcher.apply(tokenRequest); return request .toBuilder() .addHeader( "Authorization", String.format("%s %s", token.getTokenType(), token.getAccessToken())) .build(); }
@Override public HttpRequest filter(HttpRequest request) throws HttpException { checkArgument( request.getHeaders().containsKey(HOST), "request is not ready to sign; host not present"); String host = request.getFirstHeaderOrNull(HOST); String form = request.getPayload().getRawContent().toString(); checkArgument( form.indexOf(ACTION) != -1, "request is not ready to sign; Action not present %s", form); String timestamp = iso8601Timestamp.get(); String datestamp = timestamp.substring(0, 8); String service = serviceAndRegion.service(); String region = serviceAndRegion.region(host); String credentialScope = Joiner.on('/').join(datestamp, region, service, "aws4_request"); // content-type is not a required signing param. However, examples use this, so we include it to // ease testing. ImmutableMap.Builder<String, String> signedHeadersBuilder = ImmutableMap.<String, String>builder() // .put("content-type", request.getPayload().getContentMetadata().getContentType()) // .put("host", host) // .put("x-amz-date", timestamp); HttpRequest.Builder<?> requestBuilder = request .toBuilder() // .removeHeader(AUTHORIZATION) // .replaceHeader("X-Amz-Date", timestamp); if (form.indexOf(VERSION) == -1) { requestBuilder.addFormParam("Version", apiVersion); } Credentials credentials = creds.get(); if (credentials instanceof SessionCredentials) { String token = SessionCredentials.class.cast(credentials).getSessionToken(); requestBuilder.replaceHeader("X-Amz-Security-Token", token); signedHeadersBuilder.put("x-amz-security-token", token); } ImmutableMap<String, String> signedHeaders = signedHeadersBuilder.build(); String stringToSign = createStringToSign(requestBuilder.build(), signedHeaders, credentialScope); byte[] signatureKey = signatureKey(credentials.credential, datestamp, region, service); String signature = base16().lowerCase().encode(hmacSHA256(stringToSign, signatureKey)); StringBuilder authorization = new StringBuilder("AWS4-HMAC-SHA256 "); authorization .append("Credential=") .append(credentials.identity) .append('/') .append(credentialScope) .append(", "); authorization .append("SignedHeaders=") .append(Joiner.on(';').join(signedHeaders.keySet())) .append(", "); authorization.append("Signature=").append(signature); return requestBuilder.addHeader(AUTHORIZATION, authorization.toString()).build(); }