alexa-samples / skill-sample-python-fact-in-skill-purchases

Demonstrates how to use the new in-skill purchasing (ISP) features of Alexa skills by offering different packs of facts behind a purchase, and a subscription to unlock all of the packs at once.
Other
16 stars 13 forks source link

Error calling InSkillProducts API: The authentication token is invalid or doesn't have access to make this request #8

Closed Daniyaldehleh closed 1 year ago

Daniyaldehleh commented 4 years ago

Hi I did try building a version of my own, however; I ran into the mentioned error.

class GoogleIntentHandler(AbstractRequestHandler):
    def can_handle(self, handler_input):
        return ask_utils.is_intent_name("GoogleIntent")(handler_input)

    def handle(self, handler_input):
        in_skill_response=in_skill_product_response(handler_input)
        if in_skill_response:
            subscription=[
                l for l in in_skill_response.in_skill_products
                if l.reference_name == "GoogleM"]    

            if is_entitled(subscription): 
                return .speak("you are a subscribed member")
            else:
                return handler_input.response_builder.add_directive(
                    SendRequestDirective(
                        name="Buy",
                        payload= {
                            InSkillProduct: {
                                productId: "amzn1.adg.product...",
                                }
                        },
                        token= "correlationToken")
                ).respo

Error calling InSkillProducts API: The authentication token is invalid or doesn't have access to make this request

kevindra commented 4 years ago

Most likely your authorization token in the request is invalid. ISP API requires a valid auth token, see this - https://developer.amazon.com/en-US/docs/alexa/in-skill-purchase/in-skill-product-service.html#request

Reading this - https://developer.amazon.com/en-US/docs/alexa/custom-skills/request-and-response-json-reference.html#session-object

Auth token in the request is present when use is account linked. Are you using account linking? I have to check if in-skill products indeed require account linking.

Can you print the handler_input.request_envelope and check if it has the token?

Daniyaldehleh commented 4 years ago

@kevindra Thanks for your response Kevin. The account linking is on. I believe this should give some clues after printing it:

estamp': datetime.datetime(2020, 8, 27, 2, 43, 30, tzinfo=tzlocal())},
 'session': {'application': {'application_id': 'amzn1.ask.skill.78f63c60-18ac-4'},
             'attributes': None,
             'new': False,
             'session_id': 'amzn1.echo-api.session.f8b83889-',
             'user': {'access_token': None,
                      'permissions': {'consent_token': 'eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiI',
                                      'scopes': {'payments:autopay_consent': {'status': 'DENIED'}}},
                      'user_id': 'amzn1.ask.account.AEWEMZVR2'}},
 'version': '1.0'}
kevindra commented 4 years ago

I just tried building a skill and no, we don't need account linking for ISP.. Do you see apiAccessToken in the request json? handler_input.request_envelope.System.apiAccessToken

...
        "System": {
            ..
            "apiEndpoint": "https://api.amazonalexa.com",
            "apiAccessToken": "eyJ0eXAi..."
}

I think you might be missing something in your code.

Daniyaldehleh commented 4 years ago

Yes! I do get both consent token & ApiAccessToken

Daniyaldehleh commented 4 years ago

Yes! I do get both consent token & ApiAccessToken

kevindra commented 4 years ago

Okay, let me take this back to the dev team. Might be some issue with sdk or your code. In the mean time, you can always call the ISP API using an http client without the sdk - https://developer.amazon.com/en-US/docs/alexa/in-skill-purchase/in-skill-product-service.html

Daniyaldehleh commented 4 years ago

@kevindra Thank you so much! Look forward to hearing from you :)

kevindra commented 4 years ago

did you try switching to the latest version of sdk? https://github.com/danieldhz/Alexa_Timer/blob/master/lambda/requirements.txt

Daniyaldehleh commented 4 years ago

@kevindra Yes, I tried with 1.13 & 1.14

Shreyas-vgr commented 4 years ago

Hi @danieldhz, I did install ASK CLI V1 using npm install -g ask-cli@1 [Please run ask init after that to link your ASK developer account and AWS account to host lambda code]. Since currently ask add isp commands works only in CLI v1 version. I cloned the this skill sample repo using ask new --url https://github.com/alexa/skill-sample-python-fact-in-skill-purchases.git and created a new skill and renamed the isps.samples --> isps and ran ask deploy and tested the skill. The APIs work fine and I didn't get any authentication errors from the in_skill_product_response function like you mentioned.

I would suggest try the above approach and add your GoogleIntentHandlers and CancelSubscriptionHandler in lambda_function.py and edit your models/en-US.json and setup your isps using ask add isp cmd to have support for above intents and check if it works for your use case.

Daniyaldehleh commented 4 years ago

Hi @Shreyas-vgr ! I did follow your protocols and the repo works. I realized that one of the differences between the repo and my own version is that on the developer console the ISP is present on the "Linked to this skill" while mine is present only on the "Available to link ". In fact, that's what the Alexa told me my issue is too once I submitted an issue. Thus, I'd like to know how I can move an ISP from "Available to link" to "Linked to this skill"? @kevindra

Shreyas-vgr commented 4 years ago

Hi @danieldhz, maybe this doc might help to link your isp's to the skill.

Also note based on these instructions, "If any required fields are incomplete, including any required fields for each language you selected, you can save the product, but you can't yet link the new product to the skill"

Also checking with ISP service team on your vendorID: M9ATP1D4JWXUB and Skill ID: amzn1.ask.skill.78f63c60-18ac-4944-a2da-5642ad214373 provided in previous tickets, we see that the manifest information was not correct especially isChildDirected information under privacyAndCompliance, Please refer to this doc to update your manifest if you still get errors.

Daniyaldehleh commented 4 years ago

Hi @Shreyas-vgr ! Thank you so much for being responsive to my recent questions in a comprehensive manner. I cloned the https://github.com/alexa/skill-sample-python-fact-in-skill-purchases.git & swaped the ISP per your recommendation. I definitely sense I have made much progress. However, whenever I call alexa subscribe intent, I get :

JSON INPUT:

{
    "version": "1.0",
    "session": {
        "new": false,
        "sessionId": "amzn1.echo-api.session.75866a8e...dfbd16",
        "application": {
            "applicationId": "amzn1.ask.skill.8284d6...2ee412bb5"
        },
        "attributes": {
            "entitledProducts": [
                {
                    "productId": "amzn1.adg.product.0caccc4...3-48be3f6b1ffa",
                    "referenceName": "GoogleTarget",
                    "name": "Google Target",
                    "type": "SUBSCRIPTION",
                    "summary": "Google Target is a great addition because you will connect to your google calendar's.",
                    "purchasable": "NOT_PURCHASABLE",
                    "entitled": "ENTITLED",
                    "entitlementReason": "PURCHASED",
                    "activeEntitlementCount": 1,
                    "purchaseMode": "TEST"
                }
            ]
        },
        "user": {
            "userId": "amzn1.ask.account.AH5X2C4DKMDB4....YROA6FU5P3VZY2EU4F3J6Z5TJMKWA",
            "accessToken": "ya29.a0AfH6SMBbxvP1YAiflEe3G2YzQTRUA5Np...9U1A"
        }
    },
    "context": {
        "Viewports": [
            {
                "type": "APL",
                "id": "main",
                "shape": "RECTANGLE",
                "dpi": 160,
                "presentationType": "STANDARD",
                "canRotate": false,
                "configuration": {
                    "current": {
                        "video": {
                            "codecs": [
                                "H_264_42",
                                "H_264_41"
                            ]
                        },
                        "size": {
                            "type": "DISCRETE",
                            "pixelWidth": 1024,
                            "pixelHeight": 600
                        }
                    }
                }
            }
        ],
        "Viewport": {
            "experiences": [
                {
                    "arcMinuteWidth": 246,
                    "arcMinuteHeight": 144,
                    "canRotate": false,
                    "canResize": false
                }
            ],
            "shape": "RECTANGLE",
            "pixelWidth": 1024,
            "pixelHeight": 600,
            "dpi": 160,
            "currentPixelWidth": 1024,
            "currentPixelHeight": 600,
            "touch": [
                "SINGLE"
            ],
            "video": {
                "codecs": [
                    "H_264_42",
                    "H_264_41"
                ]
            }
        },
        "System": {
            "application": {
                "applicationId": "amzn1.ask.skill.8284d645-761c-4ebc-9fe8-5142ee412bb5"
            },
            "user": {
                "userId": "amzn1.ask.account.AH5X2C4DK....Q2GKMT7CYROA6FU5P3VZY2EU4F3J6Z5TJMKWA",
                "accessToken": "ya29.a0AfH6SMBbxvP1YAiflEe3G2YzQT....mQmx_QfVUGiNgO9U1A"
            },
            "device": {
                "deviceId": "amzn1.ask.device.AGSU3VEZ2AQBMZX....MFSPMXR6D3H6QXV676UZV2ZB726S",
                "supportedInterfaces": {}
            },
            "apiEndpoint": "https://api.amazonalexa.com",
            "apiAccessToken": "eyJ0eXAiOiJKV1QiLCJhbG...m2UJNek_Jz33vv2dOWL-fPCA"
        }
    },
    "request": {
        "type": "SessionEndedRequest",
        "requestId": "amzn1.echo-api.request.632.....e8-4ca9-927e-f90a52b02523",
        "timestamp": "2020-09-01T21:00:16Z",
        "locale": "en-US",
        "reason": "ERROR",
        "error": {
            "type": "INVALID_RESPONSE",
            "message": "SpeechletResponse was null"
        }
    }
}

JSON Output:

{
    "body": {
        "version": "1.0",
        "response": {
            "type": "_DEFAULT_RESPONSE"
        },
        "sessionAttributes": {
            "entitledProducts": [
                {
                    "productId": "amzn1.adg.product.0cacc..6b1ffa",
                    "referenceName": "GoogleTarget",
                    "name": "Google Target",
                    "type": "SUBSCRIPTION",
                    "summary": "Google Target is a great addition because you will connect to your google calendar's.",
                    "purchasable": "NOT_PURCHASABLE",
                    "entitled": "ENTITLED",
                    "entitlementReason": "PURCHASED",
                    "activeEntitlementCount": 1,
                    "purchaseMode": "TEST"
                }
            ]
        },
        "userAgent": "ask-python/1.14.0 Python
/3.8.4"
    }
}

Function Logs

START RequestId: 98ad105b...9682-dc2ec1c3ba9b Version: $LATEST
[INFO]  2020-09-01T21:00:46.839Z    98ad105b-...-dc2ec1c3ba9b   Starting Entitled Product Check
END RequestId: 98ad105b-7974-48f3-...3ba9b
REPORT RequestId: 98ad105b-7974...dc2ec1c3ba9b

P.s: My skill ID changed to amzn1.ask.skill.8284d645-761c-4ebc-9fe8-5142ee412bb5

nikhilym commented 4 years ago

Hey @danieldhz , can you please provide more info on this subscribe intent? a snippet of the code that is handling this intent will also help. From the request input JSON, I see that the alexa service is responding saying that a previous response is incorrect leading to SessionEndedRequest, but not sure what is the exact cause or the code process that is leading to it.

Maybe sharing the code snippet for the specific intent or mentioning the context around what is being tried in this sample skill code might help us investigate this better.

Daniyaldehleh commented 4 years ago

Sure @nikhilym The logic I am trying to accomplish is that if user already subscribed --> Say: "You are subscribed" else --> send invitation to subscribe. The intent code:

class GoogleIntentHandler(AbstractRequestHandler):
    def can_handle(self, handler_input):
        return ask_utils.is_intent_name("GoogleIntent")(handler_input)
    def handle(self, handler_input):
        in_skill_response=in_skill_product_response(handler_input)
        if in_skill_response:
            subscription=[ l for l in in_skill_response.in_skill_products
                if l.reference_name == "GoogleTarget"]    
            if is_entitled(subscription):#return true or false
                return 
            else:
                return handler_input.response_builder.add_directive(
                    SendRequestDirective(
                        name="Buy",
                        payload= {
                            "InSkillProduct": {
                                "productId": "amzn1.adg.product.0caccc...e3f6b1ffa",
                                }
                        },
                        token= "correlationToken")
                    ).response          

The rest of the code is cloned from repo

Daniyaldehleh commented 4 years ago

@nikhilym I realized the error was because I was missing a quotation from InSkillProduct. Nevertheless, I am getting a funny error from Aelxa right now. image

image as you can see alexa first works then breaks.

Daniyaldehleh commented 4 years ago

@nikhilym as well as how will i be able to customize "Good news! You already own that"? @Shreyas-vgr As well as, I am getting back the Function logs: START RequestId: b56c69ae-9198-4b6c-b56c-602779553cce Version: $LATEST

[INFO]  2020-09-03T15:56:43.227Z    b56c69ae-9198-4b6c-b56c-602779553cce    Starting Entitled Product Check
[ERROR] 2020-09-03T15:56:43.390Z    b56c69ae-9198-4b6c-b56c-602779553cce    The authentication token is invalid or doesn't have access to make this request
Traceback (most recent call last):
  File "/opt/python/lib/python3.8/site-packages/ask_sdk_runtime/dispatch.py", line 118, in dispatch
    output = self.__dispatch_request(handler_input)  # type: Union[Output, None]
  File "/opt/python/lib/python3.8/site-packages/ask_sdk_runtime/dispatch.py", line 182, in __dispatch_request
    output = supported_handler_adapter.execute(
  File "/opt/python/lib/python3.8/site-packages/ask_sdk_runtime/dispatch_components/request_components.py", line 437, in execute
    return handler.handle(handler_input)
  File "/var/task/lambda_function.py", line 360, in handle
    in_skill_response=in_skill_product_response(handler_input)
  File "/var/task/lambda_function.py", line 172, in in_skill_product_response
    return ms.get_in_skill_products(locale)
  File "/opt/python/lib/python3.8/site-packages/ask_sdk_model/services/monetization/monetization_service_client.py", line 129, in get_in_skill_products
    api_response = self.invoke(
  File "/opt/python/lib/python3.8/site-packages/ask_sdk_model/services/base_service_client.py", line 151, in invoke
    raise ServiceException(message=exception_metadata.message,
ask_sdk_model.services.service_exception.ServiceException: The authentication token is invalid or doesn't have access to make this requestEND
nikhilym commented 4 years ago

Hey @danieldhz , sorry for the late response. I pulled the feb-updates branch that you were referring to and tried the sample. As mentioned by you, I could reproduce both authentication issue as well as the issue when a product is already owned and users want to buy it again. I fixed the source code , tested it locally and pushed the changed code to feb-updates branch right now. Please try to clone the latest code and try again.

Btw, as mentioned by the official documentation for ISPs, once the ISP flow is triggered, it is handled by the service itself until the purchase is finished. The service is responding with Great! You're signed up in the above flow. Unfortunately, this is not currently updateable.

Hope this fixes your issues. Please let us know if you are still facing any problem.

aszk commented 1 year ago

Closing due to inactivity.