Skip to content
This repository has been archived by the owner on Jan 16, 2024. It is now read-only.

Commit

Permalink
Version 1.14 alexa-client-sdk
Browse files Browse the repository at this point in the history
Changes in this update:

**Enhancements**

* AudioPlayer can now pre-buffer audio tracks in the Pre-Handle stage.

**Bug Fixes**

* Fixed an issue in the SQLite wrapper code where a `SQLiteStatement` caused a memory corruption issue.
* Fixed a race condition in SpeechSynthesizer that caused crashes.
* Fixed a `cmake` issue that specifies a dependency for Bluetooth incorrectly.
* Fixed a bug that caused Bluetooth playback to start automatically.
* Changed `supportedOperations` from a vector to a set in `ExternalMediaAdapterInterface`.
* Corrected an issue where a `VolumeChanged` event had previously been sent when the volume was unchanged after `setVolume` or `adjustVolume` had been called locally.
* Fixed issue with `IterativePlaylistParser` that prevented live stations on TuneIn from playing on Android.
* Corrected the spelling of "UNINITIALIZED".

**Known Issues**

* Music playback history isn't being displayed in the Alexa app for certain account and device types.
* On GCC 8+, issues related to `-Wclass-memaccess` will trigger warnings. However, this won't cause the build to fail and these warnings can be ignored.
* Android error ("libDefaultClient.so" not found) can be resolved by upgrading to ADB version 1.0.40
* When network connection is lost, lost connection status is not returned via local TTS.
* `ACL` may encounter issues if audio attachments are received but not consumed.
* `SpeechSynthesizerState` currently uses `GAINING_FOCUS` and `LOSING_FOCUS` as a workaround for handling intermediate state. These states may be removed in a future release.
* The Alexa app doesn't always indicate when a device is successfully connected via Bluetooth.
* Connecting a product to streaming media via Bluetooth will sometimes stop media playback within the source application. Resuming playback through the source application or toggling next/previous will correct playback.
* When a source device is streaming silence via Bluetooth, the Alexa app indicates that audio content is streaming.
* The Bluetooth agent assumes that the Bluetooth adapter is always connected to a power source. Disconnecting from a power source during operation is not yet supported.
* On some products, interrupted Bluetooth playback may not resume if other content is locally streamed.
* `make integration` is currently not available for Android. In order to run integration tests on Android, you'll need to manually upload the test binary file along with any input file. At that point, the adb can be used to run the integration tests.
* On Raspberry Pi running Android Things with HDMI output audio, beginning of speech is truncated when Alexa responds to user text-to-speech (TTS).
* When the sample app is restarted and the network connection is lost, the Reminder TTS message does not play. Instead, the default alarm tone will play twice.
* `ServerDisconnectIntegratonTest` tests have been disabled until they can be updated to reflect new service behavior.
* Devices connected before the Bluetooth CA is initialized are ignored.
* The `DirectiveSequencerTest.test_handleBlockingThenImmediatelyThenNonBockingOnSameDialogId` test fails intermittently.
  • Loading branch information
mvelegon-amzn committed Jul 9, 2019
1 parent 9549185 commit 34b2a99
Show file tree
Hide file tree
Showing 59 changed files with 1,859 additions and 528 deletions.
5 changes: 5 additions & 0 deletions ACL/include/ACL/AVSConnectionManager.h
Original file line number Diff line number Diff line change
Expand Up @@ -117,6 +117,11 @@ class AVSConnectionManager
*/
void setAVSEndpoint(const std::string& avsEndpoint) override;

/**
* @return The current URL endpoint for AVS connection.
*/
std::string getAVSEndpoint();

/// @name InternetConnectionObserverInterface method overrides.
/// @{
void onConnectionStatusChanged(bool connected) override;
Expand Down
4 changes: 3 additions & 1 deletion ACL/include/ACL/Transport/MessageRouter.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright 2016-2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
* Copyright 2016-2019 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.
Expand Down Expand Up @@ -73,6 +73,8 @@ class MessageRouter

void setAVSEndpoint(const std::string& avsEndpoint) override;

std::string getAVSEndpoint() override;

void setObserver(std::shared_ptr<MessageRouterObserverInterface> observer) override;

void onConnected(std::shared_ptr<TransportInterface> transport) override;
Expand Down
9 changes: 8 additions & 1 deletion ACL/include/ACL/Transport/MessageRouterInterface.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright 2017-2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
* Copyright 2017-2019 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.
Expand Down Expand Up @@ -80,6 +80,13 @@ class MessageRouterInterface
*/
virtual void setAVSEndpoint(const std::string& avsEndpoint) = 0;

/**
* Get the URL endpoint for the AVS connection.
*
* @return The URL for the current AVS endpoint.
*/
virtual std::string getAVSEndpoint() = 0;

/**
* Set the observer to this object.
* @param observer An observer to this class, which will be notified when the connection status changes,
Expand Down
5 changes: 5 additions & 0 deletions ACL/src/AVSConnectionManager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -148,6 +148,11 @@ bool AVSConnectionManager::isConnected() const {
void AVSConnectionManager::setAVSEndpoint(const std::string& avsEndpoint) {
m_messageRouter->setAVSEndpoint(avsEndpoint);
}

std::string AVSConnectionManager::getAVSEndpoint() {
return m_messageRouter->getAVSEndpoint();
}

void AVSConnectionManager::onConnectionStatusChanged(bool connected) {
ACSDK_DEBUG5(LX(__func__).d("connected", connected));
if (!connected) {
Expand Down
34 changes: 17 additions & 17 deletions ACL/src/Transport/HTTP2Transport.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -176,7 +176,7 @@ HTTP2Transport::HTTP2Transport(
m_postConnected{false},
m_configuration{configuration},
m_disconnectReason{ConnectionStatusObserverInterface::ChangedReason::NONE} {
ACSDK_DEBUG5(LX(__func__)
ACSDK_DEBUG7(LX(__func__)
.d("authDelegate", authDelegate.get())
.d("avsEndpoint", avsEndpoint)
.d("http2Connection", http2Connection.get())
Expand Down Expand Up @@ -251,12 +251,12 @@ bool HTTP2Transport::isConnected() {
}

void HTTP2Transport::send(std::shared_ptr<MessageRequest> request) {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG7(LX(__func__));
enqueueRequest(request, false);
}

void HTTP2Transport::sendPostConnectMessage(std::shared_ptr<MessageRequest> request) {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG7(LX(__func__));
enqueueRequest(request, true);
}

Expand Down Expand Up @@ -371,7 +371,7 @@ void HTTP2Transport::onMessageRequestSent() {
std::lock_guard<std::mutex> lock(m_mutex);
m_isMessageHandlerAwaitingResponse = true;
m_countOfUnfinishedMessageHandlers++;
ACSDK_DEBUG5(LX(__func__).d("countOfUnfinishedMessageHandlers", m_countOfUnfinishedMessageHandlers));
ACSDK_DEBUG7(LX(__func__).d("countOfUnfinishedMessageHandlers", m_countOfUnfinishedMessageHandlers));
}

void HTTP2Transport::onMessageRequestTimeout() {
Expand All @@ -384,7 +384,7 @@ void HTTP2Transport::onMessageRequestTimeout() {
}

void HTTP2Transport::onMessageRequestAcknowledged() {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG7(LX(__func__));
std::lock_guard<std::mutex> lock(m_mutex);
m_isMessageHandlerAwaitingResponse = false;
m_wakeEvent.notify_all();
Expand All @@ -393,12 +393,12 @@ void HTTP2Transport::onMessageRequestAcknowledged() {
void HTTP2Transport::onMessageRequestFinished() {
std::lock_guard<std::mutex> lock(m_mutex);
--m_countOfUnfinishedMessageHandlers;
ACSDK_DEBUG5(LX(__func__).d("countOfUnfinishedMessageHandlers", m_countOfUnfinishedMessageHandlers));
ACSDK_DEBUG7(LX(__func__).d("countOfUnfinishedMessageHandlers", m_countOfUnfinishedMessageHandlers));
m_wakeEvent.notify_all();
}

void HTTP2Transport::onPingRequestAcknowledged(bool success) {
ACSDK_DEBUG5(LX(__func__).d("success", success));
ACSDK_DEBUG7(LX(__func__).d("success", success));
std::lock_guard<std::mutex> lock(m_mutex);
m_pingHandler.reset();
if (!success) {
Expand All @@ -417,7 +417,7 @@ void HTTP2Transport::onPingTimeout() {
}

void HTTP2Transport::onActivity() {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG9(LX(__func__));
std::lock_guard<std::mutex> lock(m_mutex);
m_timeOfLastActivity = std::chrono::steady_clock::now();
}
Expand All @@ -428,7 +428,7 @@ void HTTP2Transport::onForbidden(const std::string& authToken) {
}

std::shared_ptr<HTTP2RequestInterface> HTTP2Transport::createAndSendRequest(const HTTP2RequestConfig& cfg) {
ACSDK_DEBUG5(LX(__func__).d("type", cfg.getRequestType()).sensitive("url", cfg.getUrl()));
ACSDK_DEBUG7(LX(__func__).d("type", cfg.getRequestType()).sensitive("url", cfg.getUrl()));
return m_http2Connection->createAndSendRequest(cfg);
}

Expand Down Expand Up @@ -537,7 +537,7 @@ HTTP2Transport::State HTTP2Transport::handleConnecting() {
}

HTTP2Transport::State HTTP2Transport::handleWaitingToRetryConnecting() {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG7(LX(__func__));

std::chrono::milliseconds timeout = TransportDefines::RETRY_TIMER.calculateTimeToRetry(m_connectRetryCount);
ACSDK_DEBUG5(
Expand Down Expand Up @@ -602,7 +602,7 @@ HTTP2Transport::State HTTP2Transport::handleShutdown() {
}

void HTTP2Transport::enqueueRequest(std::shared_ptr<avsCommon::avs::MessageRequest> request, bool beforeConnected) {
ACSDK_DEBUG5(LX(__func__).d("beforeConnected", beforeConnected));
ACSDK_DEBUG7(LX(__func__).d("beforeConnected", beforeConnected));

if (!request) {
ACSDK_ERROR(LX("enqueueRequestFailed").d("reason", "nullRequest"));
Expand Down Expand Up @@ -638,7 +638,7 @@ void HTTP2Transport::enqueueRequest(std::shared_ptr<avsCommon::avs::MessageReque
}

HTTP2Transport::State HTTP2Transport::sendMessagesAndPings(alexaClientSDK::acl::HTTP2Transport::State whileState) {
ACSDK_DEBUG5(LX(__func__).d("whileState", whileState));
ACSDK_DEBUG7(LX(__func__).d("whileState", whileState));

std::unique_lock<std::mutex> lock(m_mutex);

Expand Down Expand Up @@ -705,7 +705,7 @@ HTTP2Transport::State HTTP2Transport::sendMessagesAndPings(alexaClientSDK::acl::

lock.lock();
} else {
ACSDK_DEBUG5(LX("m_pingHandler != nullptr"));
ACSDK_DEBUG7(LX("m_pingHandler != nullptr"));
}
}
}
Expand All @@ -722,7 +722,7 @@ bool HTTP2Transport::setStateLocked(State newState, ConnectionStatusObserverInte
ACSDK_DEBUG5(LX(__func__).d("newState", newState).d("changedReason", changedReason));

if (newState == m_state) {
ACSDK_DEBUG5(LX("alreadyInNewState"));
ACSDK_DEBUG7(LX("alreadyInNewState"));
return true;
}

Expand Down Expand Up @@ -787,7 +787,7 @@ bool HTTP2Transport::setStateLocked(State newState, ConnectionStatusObserverInte
}

void HTTP2Transport::notifyObserversOnConnected() {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG7(LX(__func__));

std::unique_lock<std::mutex> lock{m_observerMutex};
auto observers = m_observers;
Expand All @@ -799,7 +799,7 @@ void HTTP2Transport::notifyObserversOnConnected() {
}

void HTTP2Transport::notifyObserversOnDisconnect(ConnectionStatusObserverInterface::ChangedReason reason) {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG7(LX(__func__));

if (m_postConnect) {
m_postConnect->onDisconnect();
Expand All @@ -816,7 +816,7 @@ void HTTP2Transport::notifyObserversOnDisconnect(ConnectionStatusObserverInterfa
}

void HTTP2Transport::notifyObserversOnServerSideDisconnect() {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG7(LX(__func__));

if (m_postConnect) {
m_postConnect->onDisconnect();
Expand Down
18 changes: 9 additions & 9 deletions ACL/src/Transport/MessageRequestHandler.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -136,35 +136,35 @@ MessageRequestHandler::MessageRequestHandler(
m_wasMessageRequestAcknowledgeReported{false},
m_wasMessageRequestFinishedReported{false},
m_responseCode{0} {
ACSDK_DEBUG5(LX(__func__).d("context", context.get()).d("messageRequest", messageRequest.get()));
ACSDK_DEBUG7(LX(__func__).d("context", context.get()).d("messageRequest", messageRequest.get()));
}

void MessageRequestHandler::reportMessageRequestAcknowledged() {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG7(LX(__func__));
if (!m_wasMessageRequestAcknowledgeReported) {
m_wasMessageRequestAcknowledgeReported = true;
m_context->onMessageRequestAcknowledged();
}
}

void MessageRequestHandler::reportMessageRequestFinished() {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG7(LX(__func__));
if (!m_wasMessageRequestFinishedReported) {
m_wasMessageRequestFinishedReported = true;
m_context->onMessageRequestFinished();
}
}

std::vector<std::string> MessageRequestHandler::getRequestHeaderLines() {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG9(LX(__func__));

m_context->onActivity();

return {m_authHeader};
}

HTTP2GetMimeHeadersResult MessageRequestHandler::getMimePartHeaderLines() {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG9(LX(__func__));

m_context->onActivity();

Expand All @@ -186,7 +186,7 @@ HTTP2GetMimeHeadersResult MessageRequestHandler::getMimePartHeaderLines() {
}

HTTP2SendDataResult MessageRequestHandler::onSendMimePartData(char* bytes, size_t size) {
ACSDK_DEBUG5(LX(__func__).d("size", size));
ACSDK_DEBUG9(LX(__func__).d("size", size));

m_context->onActivity();

Expand All @@ -204,7 +204,7 @@ HTTP2SendDataResult MessageRequestHandler::onSendMimePartData(char* bytes, size_
} else if (m_namedReader) {
auto readStatus = AttachmentReader::ReadStatus::OK;
auto bytesRead = m_namedReader->reader->read(bytes, size, &readStatus);
ACSDK_DEBUG5(LX("attachmentRead").d("readStatus", (int)readStatus).d("bytesRead", bytesRead));
ACSDK_DEBUG9(LX("attachmentRead").d("readStatus", (int)readStatus).d("bytesRead", bytesRead));
switch (readStatus) {
// The good cases.
case AttachmentReader::ReadStatus::OK:
Expand Down Expand Up @@ -241,7 +241,7 @@ void MessageRequestHandler::onActivity() {
}

bool MessageRequestHandler::onReceiveResponseCode(long responseCode) {
ACSDK_DEBUG5(LX(__func__).d("responseCode", responseCode));
ACSDK_DEBUG7(LX(__func__).d("responseCode", responseCode));

// TODO ACSDK-1839: Provide MessageRequestObserverInterface immediate notification of receipt of response code.

Expand All @@ -256,7 +256,7 @@ bool MessageRequestHandler::onReceiveResponseCode(long responseCode) {
}

void MessageRequestHandler::onResponseFinished(HTTP2ResponseFinishedStatus status, const std::string& nonMimeBody) {
ACSDK_DEBUG5(LX(__func__).d("status", status).d("responseCode", m_responseCode));
ACSDK_DEBUG7(LX(__func__).d("status", status).d("responseCode", m_responseCode));

if (HTTP2ResponseFinishedStatus::TIMEOUT == status) {
m_context->onMessageRequestTimeout();
Expand Down
5 changes: 5 additions & 0 deletions ACL/src/Transport/MessageRouter.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -120,6 +120,11 @@ void MessageRouter::setAVSEndpoint(const std::string& avsEndpoint) {
}
}

std::string MessageRouter::getAVSEndpoint() {
std::lock_guard<std::mutex> lock{m_connectionMutex};
return m_avsEndpoint;
}

void MessageRouter::onConnected(std::shared_ptr<TransportInterface> transport) {
std::unique_lock<std::mutex> lock{m_connectionMutex};

Expand Down
18 changes: 9 additions & 9 deletions ACL/src/Transport/MimeResponseSink.cpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright 2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
* Copyright 2018-2019 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.
Expand Down Expand Up @@ -88,11 +88,11 @@ MimeResponseSink::MimeResponseSink(
m_messageConsumer{messageConsumer},
m_attachmentManager{attachmentManager},
m_attachmentContextId{std::move(attachmentContextId)} {
ACSDK_DEBUG5(LX(__func__).d("handler", handler.get()));
ACSDK_DEBUG9(LX(__func__).d("handler", handler.get()));
}

bool MimeResponseSink::onReceiveResponseCode(long responseCode) {
ACSDK_DEBUG5(LX(__func__).d("responseCode", responseCode));
ACSDK_DEBUG9(LX(__func__).d("responseCode", responseCode));

if (m_handler) {
m_handler->onActivity();
Expand All @@ -102,7 +102,7 @@ bool MimeResponseSink::onReceiveResponseCode(long responseCode) {
}

bool MimeResponseSink::onReceiveHeaderLine(const std::string& line) {
ACSDK_DEBUG5(LX(__func__).d("line", line));
ACSDK_DEBUG9(LX(__func__).d("line", line));

if (m_handler) {
m_handler->onActivity();
Expand All @@ -118,7 +118,7 @@ bool MimeResponseSink::onReceiveHeaderLine(const std::string& line) {
}

bool MimeResponseSink::onBeginMimePart(const std::multimap<std::string, std::string>& headers) {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG9(LX(__func__));

if (m_handler) {
m_handler->onActivity();
Expand Down Expand Up @@ -158,7 +158,7 @@ bool MimeResponseSink::onBeginMimePart(const std::multimap<std::string, std::str
}

HTTP2ReceiveDataStatus MimeResponseSink::onReceiveMimeData(const char* bytes, size_t size) {
ACSDK_DEBUG5(LX(__func__).d("size", size));
ACSDK_DEBUG9(LX(__func__).d("size", size));

if (m_handler) {
m_handler->onActivity();
Expand All @@ -177,7 +177,7 @@ HTTP2ReceiveDataStatus MimeResponseSink::onReceiveMimeData(const char* bytes, si
}

bool MimeResponseSink::onEndMimePart() {
ACSDK_DEBUG5(LX(__func__));
ACSDK_DEBUG9(LX(__func__));

if (m_handler) {
m_handler->onActivity();
Expand Down Expand Up @@ -208,7 +208,7 @@ bool MimeResponseSink::onEndMimePart() {
}

HTTP2ReceiveDataStatus MimeResponseSink::onReceiveNonMimeData(const char* bytes, size_t size) {
ACSDK_DEBUG5(LX(__func__).d("size", size));
ACSDK_DEBUG9(LX(__func__).d("size", size));

if (m_handler) {
m_handler->onActivity();
Expand All @@ -228,7 +228,7 @@ HTTP2ReceiveDataStatus MimeResponseSink::onReceiveNonMimeData(const char* bytes,
}

void MimeResponseSink::onResponseFinished(HTTP2ResponseFinishedStatus status) {
ACSDK_DEBUG5(LX(__func__).d("status", status));
ACSDK_DEBUG9(LX(__func__).d("status", status));

if (m_handler) {
m_handler->onResponseFinished(status, m_nonMimeBody);
Expand Down
10 changes: 10 additions & 0 deletions ACL/test/AVSConnectionManagerTest.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,7 @@ class MockMessageRouter : public MessageRouterInterface {
MOCK_METHOD0(getConnectionStatus, MessageRouterInterface::ConnectionStatus());
MOCK_METHOD1(sendMessage, void(std::shared_ptr<avsCommon::avs::MessageRequest> request));
MOCK_METHOD1(setAVSEndpoint, void(const std::string& avsEndpoint));
MOCK_METHOD0(getAVSEndpoint, std::string());
MOCK_METHOD1(setObserver, void(std::shared_ptr<MessageRouterObserverInterface> observer));
};

Expand Down Expand Up @@ -229,6 +230,15 @@ TEST_F(AVSConnectionManagerTest, test_setAVSEndpoint) {
m_avsConnectionManager->setAVSEndpoint("AVSEndpoint");
}

/**
* Test getAVSEndpoint and expect a call to messageRouter's getAVSEndpoint.
*/
TEST_F(AVSConnectionManagerTest, getAVSEndpointTest) {
auto endpoint = "AVSEndpoint";
EXPECT_CALL(*m_messageRouter, getAVSEndpoint()).Times(1).WillOnce(Return(endpoint));
ASSERT_EQ(endpoint, m_avsConnectionManager->getAVSEndpoint());
}

/**
* Test that onConnectionStatusChanged(false) results in a reconnect attempt when enabled.
*/
Expand Down
Loading

0 comments on commit 34b2a99

Please sign in to comment.