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

Issue when + sign is present in URL (Amazon SP-API, NextToken) #126

Open
GbalsaC opened this issue Feb 19, 2021 · 6 comments
Open

Issue when + sign is present in URL (Amazon SP-API, NextToken) #126

GbalsaC opened this issue Feb 19, 2021 · 6 comments

Comments

@GbalsaC
Copy link

GbalsaC commented Feb 19, 2021

aws4 v. 1.5.1
Ubuntu 20 LTS
NodeJS 12.6.9
request 2.48.5
request-promise 4.1.46

I'm currently using aws4 for Amazon SP-API (Selling partner API).

Overall, all methods work great except for one query parameter. NextToken

NextToken (Original value) is passed as a query parameter, and has the following value:
aQVM/pLGd/WaJqJYLDm0ZAmQazDrhw3CIiPeQUe9nqoU5ywFddC8C8NI3HOI22PIxqXyQLkGMBs8VhF73Xgy+zFWYRqN5/If2Yapt4MO4XEckwaFrMP2PNhNqgDpVGhEInTAy+XKVmRZBY+oaVuyc8QON+K1yc/YJ8IamK5qOBQwadZWHCdmNwFvOUDdDJWhf2GLmUGyr9UGnxD0RJmrryegoU0IPZxXMHbcorlruypW//smqbZGEWWjslwBjY4mMBO/reDY2s/v6DywD2BmVI0KxWlk275HeLE0br61/ZeG1bEi00oPms+RCEjxtHY0Jjna3DT40pCuDpTeKOS1CbZT8ssvaHo22iqc+HOHQDMXf4cGOMyIyW3zKN+nx8rxYJu46S68kxWtOgCxg3zeweCR1k9eFxFwVqnodKShpq/Y/mfOjS3d9A==

However, this returns the final query, replacing + char with %20, where the query ends looking like this:
https://sellingpartnerapi-na.amazon.com/orders/v0/orders?NextToken=aQVM%2FpLGd%2FWaJqJYLDm0ZAmQazDrhw3CIiPeQUe9nqoU5ywFddC8C8NI3HOI22PIxqXyQLkGMBs8VhF73Xgy%20zFWYRqN5%2FIf2Yapt4MO4XEckwaFrMP2PNhNqgDpVGhEInTAy%20XKVmRZBY%20oaVuyc8QON%20K1yc%2FYJ8IamK5qOBQwadZWHCdmNwFvOUDdDJWhf2GLmUGyr9UGnxD0RJmrryegoU0IPZxXMHbcorlruypW%2F%2FsmqbZGEWWjslwBjY4mMBO%2FreDY2s%2Fv6DywD2BmVI0KxWlk275HeLE0br61%2FZeG1bEi00oPms%20RCEjxtHY0Jjna3DT40pCuDpTeKOS1CbZT8ssvaHo22iqc%20HOHQDMXf4cGOMyIyW3zKN%20nx8rxYJu46S68kxWtOgCxg3zeweCR1k9eFxFwVqnodKShpq%2FY%2FmfOjS3d9A%3D%3D&MarketplaceIds=A1AM78C64UM0Y8

So, char replacement can be seen in:
+XKVmRZBY+oa becomes %20XKVmRZBY%20oa

I understand in query, + sign becomes a space, and probably %2B should be used instead, my question is, how should I add the parameter into the sign method if the original has a + char, should I replace it before passing? or should I replace it after the path is returned from sign()

My complete code is the following:

import aws4 from "aws4";
import { RequestPromiseAPI } from "request-promise";

const _requestWrapper<T>(opts: { host: string; path: string; method: string; headers: Headers }): Promise<T> {
    return this.request(`https://${opts.host}${opts.path}`, {
      method: opts.method,
      headers: opts.headers,
      json: true,
      resolveWithFullResponse: true,
    }).then((response) => {
      console.log('<SP-API> Response Headers: ', response.headers);
      const d: T = response.body;
      console.log('<SP-API> Response BODY: ', d);
      return d;
    })
  }

// >> Where nextToken is the one posted as "Original"
async getOrder(nextToken:string){
   const ss = aws4.sign(
      {
        host: `sellingpartnerapi-na.amazon.com`,
        method: "GET",
        path: `/orders/v0/orders?NextToken=${nextToken}&MarketplaceIds=A1AM78C64UM0Y8`,
        region: "us-east-1",
        service: "execute-api",
        headers: {
          "User-Agent": "Fiscalpop/2.0 (Language=JavaScript; Platform=Ubuntu/16)",
          'x-amz-access-token': tokenized.access_token
        },
      },
      {
        accessKeyId: "ASIA2PIENJRBC...",
        secretAccessKey: "IePqZ5lBHhrJdzQbqyZ8U5t0...",
        sessionToken: "FwoGZXIvYXdzED8aDKQUTa4ly/nPYc+PuSKqAfQd60R...",
      }
    );
    return _requestWrapper<{ payload: SP_Order }>(ss);
}
@mhart
Copy link
Owner

mhart commented Feb 19, 2021

What's converting the + into %20?

@GbalsaC
Copy link
Author

GbalsaC commented Feb 19, 2021

The returned aws4.sign() path value has the + replaced with %20.

From the above code, If I do a console.log('ss: ', ss) where ss is the variable returned from the aws4.sign() method:

Original NextToken:
gtaZal63YIiaJqJYLDm0ZAmQazDrhw3CgJalwszeUhoU5ywFddC8C8NI3HOI22PIxqXyQLkGMBs8VhF73Xgy+zFWYRqN5/IfQ/jTgP4cXDpuvG9fmlR56zT99DMY0KuTInTAy+XKVmRZBY+oaVuyc8QON+K1yc/Yfb9rRgL4TdE0EBf7igWxmmRLuJ4BeSGYf2GLmUGyr9UGnxD0RJmrryegoU0IPZxXv6JqHKIDsst6Zei4iUx8iJbwRJ+1RJ66MBO/reDY2s/v6DywD2BmVI0KxWlk275HeLE0br61/ZeG1bEi00oPms+RCEjxtHY0TuNAtmdHevXpo/P/8H1yryuTIyiVCSA2bGl11BXVovsrAC7MwVMzx+UDRT6zkDPnSJxHPsySa7tPoHVKB7NbV61OyEkQXs58jYa3TOdM+ra8ZiM67cQNng==

ss:  {
  host: 'sellingpartnerapi-na.amazon.com',
  method: 'GET',
  path: '/orders/v0/orders?NextToken=gtaZal63YIiaJqJYLDm0ZAmQazDrhw3CgJalwszeUhoU5ywFddC8C8NI3HOI22PIxqXyQLkGMBs8VhF73Xgy%20zFWYRqN5%2FIfQ%2FjTgP4cXDpuvG9fmlR56zT99DMY0KuTInTAy%20XKVmRZBY%20oaVuyc8QON%20K1yc%2FYfb9rRgL4TdE0EBf7igWxmmRLuJ4BeSGYf2GLmUGyr9UGnxD0RJmrryegoU0IPZxXv6JqHKIDsst6Zei4iUx8iJbwRJ%201RJ66MBO%2FreDY2s%2Fv6DywD2BmVI0KxWlk275HeLE0br61%2FZeG1bEi00oPms%20RCEjxtHY0TuNAtmdHevXpo%2FP%2F8H1yryuTIyiVCSA2bGl11BXVovsrAC7MwVMzx%20UDRT6zkDPnSJxHPsySa7tPoHVKB7NbV61OyEkQXs58jYa3TOdM%20ra8ZiM67cQNng%3D%3D&MarketplaceIds=A1AM78C64UM0Y8',
  region: 'us-east-1',
  service: 'execute-api',
  headers: {
    'User-Agent': 'Fiscalpop/2.0 (Language=JavaScript; Platform=Ubuntu/16)',
    'x-amz-access-token': 'Atza|IwEBIDpYYDWUQ_r-iiRtwgxesg50OBOAhYGcY3Cd0Xl2Uh1T9...',
    Host: 'sellingpartnerapi-na.amazon.com',
    'X-Amz-Security-Token': 'FwoGZXIvYXdzEKD//////////wEaDCe1a8JIcLAD6B5a6iKqAU4M5...',
    'X-Amz-Date': '20210219T230345Z',
    Authorization: 'AWS4-HMAC-SHA256 Credential=ASIA2PIENJRBKGWCAJJ3/20210219/us-east-1/execute-api/aws4_request, SignedHeaders=host;x-amz-access-token;x-amz-date;x-amz-security-token, Signature=392f6da19a053af7b32f34578...'
  }
}

You'll see the %20 replaced the + inputs

@GbalsaC
Copy link
Author

GbalsaC commented Feb 19, 2021

If I replace the + in NextToken's original value with %2B the query will pass correctly.

Something like this: NextToken=${queries.NextToken.split('+').join('%2B')}

const ss = aws4.sign(
      {
        host: this.ENDPOINT,
        method: "GET",
        path: `/orders/v0/orders?&MarketplaceIds=A1AM78C64UM0Y8&NextToken=${queries.NextToken.split('+').join('%2B')}`,
        region: "us-east-1",
        service: "execute-api",
        headers: {
          "User-Agent": "Fiscalpop/2.0 (Language=JavaScript; Platform=Ubuntu/16)",
          'x-amz-access-token': tokenized.access_token
        },
      },
      {
        accessKeyId: "ASIA2PIENJRBCFHH...",
        secretAccessKey: "IePqZ5lBHhrJdzQbqyZ8U5t0eRgz6SjIn...",
        sessionToken: "FwoGZXIvYXdzED8aDKQUTa4ly/nPYc+PuSKqAfQd60RsmIwhrqH...",
      }
    );

Then the returned path value keeps the %2B values and signs correctly.
NextToken=CqT3Z2T9h1iaJqJYLDm0ZAmQazDrhw3CgJalwszeUhoU5ywFddC8C8NI3HOI22PIxqXyQLkGMBs8VhF73Xgy%2BzFWYRqN5%2FIfQ%2FjTgP4cXDpsHZtqbATNf3sogY7TweHPInTAy%2BXKVmRZBY%2BoaVuyc8QON%2BK1yc%2FYfb9rRgL4TdE0EBf7igWxmmRLuJ4BeSGYf2GLmUGyr9UGnxD0RJmrryegoU0IPZxXv6JqHKIDsst6Zei4iUx8iJbwRJ%2B1RJ66MBO%2FreDY2s%2Fv6DywD2BmVI0KxWlk275HeLE0br61%2FZeG1bEi00oPms%2BRCEjxtHY06ULiqinMRi1cjS%2FwODfiaNDlIVQVL%2BxW02hnPs00iV1GIfz4O%2BfU3p%2F7qvexBJaVfgRJHzL0fOvwK4TCp4Ag0EdDnjhHuqvYnjahUXM24sdp4r5C1zkSUg%3D%3D&MarketplaceIds=A1AM78C64UM0Y8

And I'm able to receive the query response using the token.

Otherwise, without replacing the + char in the parameter before passing it to sign(), I get an error:

We could not decode your NextToken. Possible reasons include: a transmission error, improper quoting or a truncation problem.

@PrashantMalaviya
Copy link

hello @GbalsaC sir
it is also notworking!!!!!!

{'errors': [{'message': None, 'code': 'InvalidInput'}]}

@mavrick951
Copy link

Python 3.x
import sys, os, base64, datetime, hashlib, hmac ,json
import requests
from datetime import date
Amazon Example to sending and signing a request from python, heavily modified for enterprise application.

GbalsaC,
I have the same issue, i solved it with the %2B being replaced before sending the string to be signed.
As you had encountered, using the other %20 caused a malformed or broken token response from AWS. Another response i got was that the message was null as PrashantMalaviya has indicated above.
I am using

@AruEnvista
Copy link

Python 3.x import sys, os, base64, datetime, hashlib, hmac ,json import requests from datetime import date Amazon Example to sending and signing a request from python, heavily modified for enterprise application.

GbalsaC, I have the same issue, i solved it with the %2B being replaced before sending the string to be signed. As you had encountered, using the other %20 caused a malformed or broken token response from AWS. Another response i got was that the message was null as PrashantMalaviya has indicated above. I am using

Hi, I am getting Same issue that was discuuing here, Any final conclusion on te same? I am using java

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

No branches or pull requests

5 participants