/* * Copyright 2010-2016 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Licensed under the Apache License, Version 2.0 (the "License"). * You may not use this file except in compliance with the License. * A copy of the License is located at * * http://aws.amazon.com/apache2.0 * * or in the "license" file accompanying this file. This file is distributed * on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either * express or implied. See the License for the specific language governing * permissions and limitations under the License. */ package com.amazonaws.services.polly; import com.amazonaws.AmazonClientException; import com.amazonaws.auth.AWSCredentials; import com.amazonaws.auth.AWSCredentialsProvider; import com.amazonaws.regions.Region; import com.amazonaws.regions.Regions; import com.amazonaws.services.polly.model.OutputFormat; import com.amazonaws.services.polly.model.SynthesizeSpeechPresignRequest; import com.amazonaws.services.polly.model.TextType; import com.amazonaws.services.polly.model.VoiceId; import org.apache.http.NameValuePair; import org.apache.http.client.utils.URLEncodedUtils; import org.junit.Assert; import org.junit.Before; import org.junit.Test; import java.net.URI; import java.net.URISyntaxException; import java.util.*; import static org.mockito.Mockito.*; public class AmazonPollyPresigningClientTest { private static final String HOST = "localhost"; private static final String SCHEME = "http"; private static final String RESOURCE_PATH = "/v1/speech"; private static final int PORT = 9080; private static final String SERVICE_NAME = "polly"; private static final String ACCESS_KEY = "access-key"; private static final String SECRET_KEY = "secret-key"; private static final String INPUT_TEXT = "<speak>Mary has a little lamb</speak>"; private static final String SSML_TEXT_TYPE = TextType.Ssml.toString(); private static final String SALLI_VOICE_ID = VoiceId.Salli.toString(); private static final String MP3_OUTPUT_FORMAT = OutputFormat.Mp3.toString(); private static final String LEXICON_NAME_1 = "lexiconName1"; private static final String LEXICON_NAME_2 = "lexiconName2"; private static final String TEXT_KEY = "Text"; private static final String TEXT_TYPE_KEY = "TextType"; private static final String VOICE_ID_KEY = "VoiceId"; private static final String OUTPUT_FORMAT_KEY = "OutputFormat"; private static final String LEXICON_NAME_KEY = "LexiconName"; private static final String X_AMZN_ALGORITHM_KEY = "X-Amz-Algorithm"; private static final String X_AMZN_DATE_KEY = "X-Amz-Date"; private static final String X_AMZN_SIGNED_HEADERS_KEY = "X-Amz-SignedHeaders"; private static final String X_AMZN_EXPIRES_KEY = "X-Amz-Expires"; private static final String X_AMZN_CREDENTIAL_KEY = "X-Amz-Credential"; private static final String X_AMZN_SIGNATURE_KEY = "X-Amz-Signature"; private Set<String> expectedQueryParameterKeys; private Map<String, String> expectedQueryParameterPairs; private AmazonPollyPresigningClient client; private SynthesizeSpeechPresignRequest request; private AWSCredentials credentials; private AWSCredentialsProvider credentialsProvider; @Before public void setup() { expectedQueryParameterKeys = new HashSet<String>(Arrays.asList( TEXT_KEY, TEXT_TYPE_KEY, VOICE_ID_KEY, OUTPUT_FORMAT_KEY, X_AMZN_ALGORITHM_KEY, X_AMZN_DATE_KEY, X_AMZN_SIGNED_HEADERS_KEY, X_AMZN_EXPIRES_KEY, X_AMZN_CREDENTIAL_KEY, X_AMZN_SIGNATURE_KEY )); expectedQueryParameterPairs = Collections.unmodifiableMap(new HashMap<String, String>() { { put(TEXT_KEY, INPUT_TEXT); put(TEXT_TYPE_KEY, SSML_TEXT_TYPE); put(VOICE_ID_KEY, SALLI_VOICE_ID); put(OUTPUT_FORMAT_KEY, MP3_OUTPUT_FORMAT); } }); credentials = mock(AWSCredentials.class); when(credentials.getAWSAccessKeyId()).thenReturn(ACCESS_KEY); when(credentials.getAWSSecretKey()).thenReturn(SECRET_KEY); credentialsProvider = mock(AWSCredentialsProvider.class); when(credentialsProvider.getCredentials()).thenReturn(credentials); client = new AmazonPollyPresigningClient(credentialsProvider); client.setServiceNameIntern(SERVICE_NAME); client.setRegion(Region.getRegion(Regions.US_EAST_1)); client.setEndpoint(String.format("%s://%s:%d", SCHEME, HOST, PORT)); request = new SynthesizeSpeechPresignRequest() .withText(INPUT_TEXT) .withTextType(SSML_TEXT_TYPE) .withOutputFormat(MP3_OUTPUT_FORMAT) .withVoiceId(SALLI_VOICE_ID); } @Test public void testGetPresignedUrl() throws URISyntaxException { URI uri = client.getPresignedSynthesizeSpeechUrl(request).toURI(); verifyCredentialsMocks(); assertBasicUriValues(uri); List<NameValuePair> params = URLEncodedUtils.parse(uri, "UTF-8"); for (NameValuePair pair : params) { Assert.assertTrue("Unexpected query parameter: " + pair.getName(), expectedQueryParameterKeys.contains(pair.getName())); expectedQueryParameterKeys.remove(pair.getName()); if (expectedQueryParameterPairs.containsKey(pair.getName())) { Assert.assertEquals(expectedQueryParameterPairs.get(pair.getName()), pair.getValue()); } } Assert.assertTrue("Missing expected parameters: " + expectedQueryParameterKeys.toString(), expectedQueryParameterKeys.isEmpty()); } @Test public void testGetPresignedUrlWithOneLexicon() throws URISyntaxException { List<String> lexiconsNamesExpected = new ArrayList<String>(Arrays.asList(LEXICON_NAME_1)); request.setLexiconNames(lexiconsNamesExpected); expectedQueryParameterKeys.add(LEXICON_NAME_KEY); URI uri = client.getPresignedSynthesizeSpeechUrl(request).toURI(); verifyCredentialsMocks(); assertBasicUriValues(uri); List<NameValuePair> params = URLEncodedUtils.parse(uri, "UTF-8"); for (NameValuePair pair : params) { Assert.assertTrue("Unexpected query parameter: " + pair.getName(), expectedQueryParameterKeys.contains(pair.getName())); if (LEXICON_NAME_KEY.equals(pair.getName())) { Assert.assertTrue("Unexpected lexicon name: " + pair.getValue(), lexiconsNamesExpected.contains(pair.getValue())); lexiconsNamesExpected.remove(pair.getValue()); } } Assert.assertTrue("Not all lexicons names were included " + lexiconsNamesExpected.toString(), lexiconsNamesExpected.isEmpty()); } @Test(expected=AmazonClientException.class) public void testGetPresignedUrlWithMultipleLexicons() throws URISyntaxException { List<String> lexiconsNamesExpected = new ArrayList<String>( Arrays.asList(LEXICON_NAME_1, LEXICON_NAME_2)); request.setLexiconNames(lexiconsNamesExpected); } @Test public void testGetPresignedUrlWithoutTextType() throws URISyntaxException { request.setTextType((String) null); expectedQueryParameterKeys.remove(TEXT_TYPE_KEY); URI uri = client.getPresignedSynthesizeSpeechUrl(request).toURI(); verifyCredentialsMocks(); assertBasicUriValues(uri); List<NameValuePair> params = URLEncodedUtils.parse(uri, "UTF-8"); for (NameValuePair pair : params) { Assert.assertTrue("Unexpected query parameter: " + pair.getName(), expectedQueryParameterKeys.contains(pair.getName())); expectedQueryParameterKeys.remove(pair.getName()); } Assert.assertTrue("Missing expected parameters: " + expectedQueryParameterKeys.toString(), expectedQueryParameterKeys.isEmpty()); } @Test public void testGetPresignedUrlWithRequestCredentialsProvider() throws URISyntaxException { AWSCredentialsProvider requestCredentialsProvider = mock(AWSCredentialsProvider.class); when(requestCredentialsProvider.getCredentials()).thenReturn(credentials); request.setRequestCredentials(requestCredentialsProvider.getCredentials()); URI uri = client.getPresignedSynthesizeSpeechUrl(request).toURI(); verify(requestCredentialsProvider).getCredentials(); assertBasicUriValues(uri); } private void verifyCredentialsMocks() { verify(credentialsProvider).getCredentials(); verify(credentials).getAWSAccessKeyId(); verify(credentials).getAWSSecretKey(); } private void assertBasicUriValues(URI uri) { Assert.assertEquals(SCHEME, uri.getScheme()); Assert.assertEquals(HOST, uri.getHost()); Assert.assertEquals(PORT, uri.getPort()); Assert.assertEquals(RESOURCE_PATH, uri.getPath()); } }