/// <summary> /// Generate a presigned URL based on a <see cref="SynthesizeSpeechRequest"/>. /// </summary> /// <param name="credentials">The credentials to use in the presigned URL.</param> /// <param name="region">The region for the URL.</param> /// <param name="request">The request to base the presigned URL on.</param> /// <returns></returns> public static string GeneratePresignedUrl(AWSCredentials credentials, RegionEndpoint region, SynthesizeSpeechRequest request) { if (credentials == null) throw new ArgumentNullException("credentials"); if (region == null) throw new ArgumentNullException("region"); if (request == null) throw new ArgumentNullException("request"); // Marshall this request and prepare it to be signed var marshaller = new SynthesizeSpeechRequestMarshaller(); var iRequest = marshaller.Marshall(request); iRequest.UseQueryString = true; iRequest.HttpMethod = HTTPGet; iRequest.Endpoint = new UriBuilder(HTTPS, region.GetEndpointForService(PollyServiceName).Hostname).Uri; iRequest.Parameters[XAmzExpires] = ((int)FifteenMinutes.TotalSeconds).ToString(CultureInfo.InvariantCulture); if (request.IsSetLexiconNames()) { var sortedLexiconNames = new List<string>(request.LexiconNames); sortedLexiconNames.Sort(StringComparer.Ordinal); iRequest.Parameters[LexiconNamesParameter] = JsonMapper.ToJson(sortedLexiconNames); } if (request.IsSetOutputFormat()) iRequest.Parameters["OutputFormat"] = request.OutputFormat.ToString(); if (request.IsSetSampleRate()) iRequest.Parameters["SampleRate"] = request.SampleRate.ToString(); if (request.IsSetText()) iRequest.Parameters["Text"] = request.Text; if (request.IsSetTextType()) iRequest.Parameters["TextType"] = request.TextType.ToString(); if (request.IsSetVoiceId()) iRequest.Parameters["VoiceId"] = request.VoiceId; var immutableCredentials = credentials.GetCredentials(); if (immutableCredentials.UseToken) { // Don't use HeaderKeys.XAmzSecurityTokenHeader because Polly treats this as case-sensitive iRequest.Parameters["X-Amz-Security-Token"] = immutableCredentials.Token; } // Only the host header should be signed, and the signer adds that. // So clear out headers. iRequest.Headers.Clear(); // Create presigned URL and assign it var signingResult = SynthesizeSpeechPresignedUrlSigner.SignSynthesizeSpeechRequest(iRequest, new RequestMetrics(), immutableCredentials.AccessKey, immutableCredentials.SecretKey, PollyServiceName, region.SystemName); var authorization = "&" + signingResult.ForQueryParameters; return ComposeUrl(iRequest).AbsoluteUri + authorization; }