Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

AudioPlayer Interface doesn't support HTTP Authorization header (in fact any of HTTP headers) along with the audio file URL #610

Open
voiceactivity opened this issue Feb 10, 2020 · 22 comments

Comments

@voiceactivity
Copy link

voiceactivity commented Feb 10, 2020

Hi team,
About 6 months ago we published the Sound Drive skill. This skill allows users to play their own audio files from their Google Drive accounts. The skill uses AudioPlayer Interface.

Many people (including those ones with Premium subscriptions) were enjoying this skill until now. But now we have no other choice but shut it down.
The reason for that is the change Google recently made in the Google Drive API.
In the past Google allowed downloading files with the access_token attached to the HTTP GET request as a parameter.
So, our Play Directive looked like this:
{ "type": "AudioPlayer.Play", "playBehavior": "valid playBehavior value such as ENQUEUE", "audioItem": { "stream": { "url": "https://www.googleapis.com/drive/v3/files/1ke4YoCoroY3YYD9tLUvrhv_WjiUZFbJY?alt=media&access_token=ya29.ImG9B...", "token": "opaque token representing this stream", "expectedPreviousToken": "opaque token representing the previous stream", "offsetInMilliseconds": 0, ... }
This way the AudioPlayer was requesting the file from Google Drive providing a valid access token.

Now, it does require that the access_token been passed inside the Authorization HTTP header. For example - Authorization: Bearer ya29.Im.....
Actually, Google was the last who deprecated this feature - passing the access_token in the HTTP GET request.

Unfortunately, the AudioPlayer Interface (Alexa Skill SDK) doesn't support that: https://developer.amazon.com/en-US/docs/alexa/custom-skills/audioplayer-interface-reference.html#play

According to the CloudWatch logs, Alexa uses this: AlexaMediaPlayer/2.1.3131.0 (Linux;Android 5.1.1) ExoPlayerLib/1.5.9

In particular, the ExoPlayerLib provides extensive supports of HTTP headers in the request:
https://github.com/google/ExoPlayer
https://github.com/google/ExoPlayer/blob/76962d50f1d80941d6768e4e765fa4ff010705e7/library/core/src/main/java/com/google/android/exoplayer2/upstream/DataSpec.java
https://github.com/google/ExoPlayer/blob/76962d50f1d80941d6768e4e765fa4ff010705e7/library/core/src/main/java/com/google/android/exoplayer2/upstream/DefaultHttpDataSource.java

Having the AudioPlayer Interface without HTTP headers support is like trying to spend $1000 000 in the $0.99 shop.

Could you please consider to implement that?
Until then, we are shutting down our Skill and the service.

Thank you!

@ghost
Copy link

ghost commented Feb 10, 2020

Hang on, I think you are rather over-panicking here

https://cloud.google.com/blog/products/application-development/upcoming-changes-to-the-google-drive-api-and-google-picker-api

Here’s what we recommend you do if authentication with the HTTP header is not possible:

For file downloads, redirect to the webContentLink which will instruct the browser to download the content. If the application wants to display the file to the user, they can simply redirect to the alternateLink in v2 or webViewLink in v3.

For file exports, redirect to the export link in exportLinks with the desired mime type which will instruct the browser to download the content.

Also, can you just not make a pre-request to get a temporary download link, like you have to do with pre-signed downloads via S3?

There's a definitely a solution here....

@voiceactivity
Copy link
Author

voiceactivity commented Feb 10, 2020 via email

@voiceactivity
Copy link
Author

voiceactivity commented Feb 10, 2020 via email

@ShenChen93
Copy link
Contributor

Hi Paul @voiceactivity

Thanks for posting this issue. Cause this feature request need APIs support and then we could release new SDK models, I reached out to internal service team and delivered your demand. Right now all relevant team start looking into it.

I will keep this issue open for now, and please keep tuned :)

Thanks,
Shen

@voiceactivity
Copy link
Author

voiceactivity commented Feb 17, 2020 via email

@voiceactivity
Copy link
Author

Have you given up on this request?

@voiceactivity
Copy link
Author

Hi @ShenChen-Amazon I hope you're doing well. Any updates for this request?
Thank you

@ShenChen93
Copy link
Contributor

@voiceactivity ,

Thanks for being patient. Unfortunately, at this moment, we haven't heard any updates from services team about this feature release. I will post updates here once this feature released to public.

Thanks,
Shen

@voiceactivity
Copy link
Author

voiceactivity commented Apr 30, 2020

Hi @ShenChen-Amazon ,

Any chance to get a direct contact of anybody in charge in the service team?
It's really shame that we are loosing such a great opportunity right now by postponing the fix.

Cheers,
Paul

@ShenChen93
Copy link
Contributor

@voiceactivity ,

I am very sorry for the delay. You could log the issue on forums: https://alexa.uservoice.com/forums/906892-alexa-skills-developer-voice-and-vote if you want to contact with the service team directly.

Thanks,
Shen

@voiceactivity
Copy link
Author

voiceactivity commented May 1, 2020

We have done this already, a couple of months ago. Dead quiet.
Posted there another comment.
But , to be honest, I've started giving up in my hope that feature will ever be implemented and our skill could be resurrected. I cannot see that Amazon is interested in it.

Thank you,

@voiceactivity
Copy link
Author

Looks like the latest AVS AudioPlayer v1.5 added this feature: https://developer.amazon.com/en-US/docs/alexa/alexa-voice-service/audioplayer.html#version-changes

Support for passing HTTP header information in an audio stream, enabling DRM and other authenticated resources :

{
"header": {
"namespace": "AudioPlayer",
"name": "Play",
"messageId": "{{STRING}}",
"dialogRequestId": "{{STRING}}"
},
"payload": {
...
],
"audioItem": {
"audioItemId": "{{STRING}}",
...
"caption": {
"content": "{{STRING}}",
"type": "{{STRING}}"
},
"httpHeaders": {
"manifest": [
{
"name:": "{{STRING}}",
"value:": "{{STRING}}"
}

],...

Is it what we're waiting for from the Service team?
That would be awesome.

Thank you

@ShenChen93
Copy link
Contributor

Hi @voiceactivity .

Yep, this feature is supported in AudioPlayer v1.5. However, the interface haven't been updated yet: https://developer.amazon.com/en-US/docs/alexa/custom-skills/audioplayer-interface-reference.html, pleaes keep tunned.

Thanks,
Shen

@abhjroy
Copy link
Contributor

abhjroy commented Aug 16, 2022

Hi @voiceactivity is this ticket is still relevant?

@pfilippov
Copy link

Hi, yes, of course. However there is still no change been made in the ASK to support that update.
Thank you

@RobinBeismann
Copy link

Any idea when this feature comes?

@warren-bank
Copy link

warren-bank commented Mar 25, 2023

Hi. I'm brand new to Alexa skills. It blows my mind that this issue even exists.. I mean, the AI interaction models are amazing.. but to not implement something so basic as providing a way to secure the audio streams that a skill will ultimately access on behalf of the user.. it's just odd.

Anyway.. I just took a quick look at the code in this repo.. where support for this feature should be included and exposed through the JS API:


..and it seems to me that in a Lambda.. as a janky workaround.. wouldn't this work?

{
  const response = handlerInput.responseBuilder
    // ...
    .getResponse()

  if (response.directives) {
    response.directives.forEach(directive => {
      if (directive.type === 'AudioPlayer.Play') {
        directive.audioItem.stream.httpHeaders = {
          "all": [{
            "name":  "",
            "value": ""
          }]
        }
      }
    })
  }

  return response
}

..I haven't tested it yet, but will soon

@pfilippov
Copy link

Hi, the future you're referring to implemented in AVS (Alexa Voice Services) Audio Interface v.1.5 in about 1 year ago. The next step should be done be Alexa Skills team to make it a part of Alexa Skills SDK.
So, your code just won't work, because AVS and Alexa Skills SDK are different things.
Looks like Alexa Skills team is very reluctant to implement this feature. Don't know why.
It's not very difficult, considering the fact that AVS v.1.5 already supports it.
Anyway, give it a go and post an update 🙂

@warren-bank
Copy link

I just tested my proposed workaround.. and it does work.

I pushed a demo Alexa skill to this repo..
and (at least for right now) this skill is in the default branch..
so you can test it yourself by creating a new custom skill (in the Alexa Developer Console)..
and cloning from: https://github.com/warren-bank/Alexa-skill-demos.git

In order to perform the test, this points the URL for an audio stream at a public URL from requestbin.com.. which allows a log of the request to be easily examined.

I'm not sure how long these logs remain available, but you can see my test result here.

The test header was received by the server, which would (typically) be hosting the audio file:

x-alexa-issue: https://github.com/alexa/alexa-skills-kit-sdk-for-nodejs/issues/610#issuecomment-1483729767

@pfilippov
Copy link

Hi Warren, thanks, looking at the log it seems that it works 👍
I will try that too.
Thank you

@warren-bank
Copy link

For my own needs.. and anybody else who may be interested in using it.. I'm in the process right now of packaging this up as a tiny npm module with a clean API. It'll be on npm in less than an hour.

@warren-bank
Copy link

warren-bank commented Mar 25, 2023

ok.. it's ready to go

  • npm repo
  • git repo
  • updated demo skill to use the external npm dependency
    • which can still be imported by the Alexa Console from:
      https://github.com/warren-bank/Alexa-skill-demos.git
  • same HTTP request log that shows the demo is still working
    • note: there are 2x new requests logged
      1. this line is commented...
        and the default HTTP headers are included in the request,
        along with the additional headers added by the following line
      2. the line is uncommented...
        and the default HTTP headers are removed before new headers are added

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

6 participants