Reputation: 11
I am working on integrating my application Walmart Marketplace API using Ruby on Rails.
1. if i try to generate Auth signature for multiple parameters, it does not generate it and returns exceptions. I am using a Jar file to generate Auth signature
For e.g. -: https://marketplace.walmartapis.com/v3/orders?createdStartDate=2016-09-13&createdEndDate=2016-09-23
Does anyone generate Auth Signature & timestamp for multiple parameter for Walmart Marketplace API
2. Does Auth Signature & timestamp need to be generated for each API call for e.g . Pagination call Also?
Upvotes: 1
Views: 2117
Reputation: 126
Additional Comments
I know it is a month later and you already have your program figured out but in case you need some help with these parts or anyone else does, I thought I would include the following information I have on the Walmart API.
1.You might want to consider building a method in ruby since it'll be more interactive with the rest of your ruby program, it was kind of difficult but when I was doing it the most difficult part was wrapping the string in the with the SHA256 digest of string to sign. So I threw together a few methods and it works:
pem = make_pem('PRIVATE KEY', encodedKeyBytes)
digest = OpenSSL::Digest::SHA256.new
pkey = OpenSSL::PKey::RSA.new(pem)
signature = pkey.sign(digest, stringToSign)
def make_pem(tag, der)
box tag, Base64.strict_encode64(der).scan(/.{1,64}/)
end
def box(tag, lines)
lines.unshift "-----BEGIN #{tag}-----"
lines.push "-----END #{tag}-----"
lines.join("\n")
end
It's not perfect but ruby doesn't really have the functionality built in so you have to change it around to get it to work. If this still doesn't work feel free to contact me, but I started out using the jar they provide and I promise it is necessary when you are making thousands of different calls a day with different parameters and urls to be able to find the point of failure and if it isn't in ruby its going to be a lot harder to work with and fix.
2/3. You already answered that these need to be included in every call to the API and I don't really have anything else to add here except to not try to find a way around this, like submitting the same time stamp for a batch of calls. Even though it might work if the calls are made within a certain time window, Walmart uses the time stamp to determine which call came in last which is especially important for things like their price API. Again feel free to email me with any questions, I'll try to respond here too but I don't this website that often.
The variable names I am using these variable names just to reference the code provided in the walmart developer guide. I am just going to translate the java code there to ruby to show how I got the values for stringToSign and encodedKeyBytes.
# This is provided to you by walmart
consumerId = "b68d2a72...."
# Also provided by walmart
privateEncodedStr = "MIICeAIBADANBgkqhkiG9w0BAQEFAA......"
# Full path
baseUrl = "https://marketplace.walmartapis.com/v2/feeds"
# HTTP Method Verb
httpMethod = "GET"
timestamp = (Time.now.to_f * 1000).to_i.to_s
stringToSign = consumerId + "\n" + baseUrl + "\n" + httpMethod + "\n" + timestamp + "\n"
encodedKeyBytes = Base64.decode64(privateEncodedStr)
From there you just run it through the original code and then base64 encode the signature and remove white spaces and then you're good to make a request.
Upvotes: 3
Reputation: 1
if i try to generate Auth signature for multiple parameters, it does not generate it and returns exceptions. I am using a Jar file to generate Auth signature. USE SHA class instead of jar file => It will generate signature for multiple parameters also.
import org.apache.commons.codec.binary.Base64;
import java.security.KeyFactory;
import java.security.PrivateKey;
import java.security.Signature;
import java.security.spec.PKCS8EncodedKeySpec;
public class SHA256WithRSAAlgo { private static String consumerId = "b68d2a72...."; // Trimmed for security reason private static String baseUrl = "https://marketplace.walmartapis.com/v2/feeds"; private static String privateEncodedStr = "MIICeAIBADANBgkqhkiG9w0BAQEFAA......"; //Trimmed for security reasons public static void main(String[] args) { String httpMethod = "GET"; String timestamp = String.valueOf(System.currentTimeMillis()); String stringToSign = consumerId + "\n" + baseUrl + "\n" + httpMethod + "\n" + timestamp + "\n"; String signedString = SHA256WithRSAAlgo.signData(stringToSign, privateEncodedStr); System.out.println("Signed String: " + signedString); } public static String signData(String stringToBeSigned, String encodedPrivateKey) { String signatureString = null; try { byte[] encodedKeyBytes = Base64.decodeBase64(encodedPrivateKey); PKCS8EncodedKeySpec privSpec = new PKCS8EncodedKeySpec(encodedKeyBytes); KeyFactory kf = KeyFactory.getInstance("RSA"); PrivateKey myPrivateKey = kf.generatePrivate(privSpec); Signature signature = Signature.getInstance("SHA256withRSA"); signature.initSign(myPrivateKey); byte[] data = stringToBeSigned.getBytes("UTF-8"); signature.update(data); byte[] signedBytes = signature.sign(); signatureString = Base64.encodeBase64String(signedBytes); } catch (Exception e) { e.printStackTrace(); } return signatureString; } }
Does Auth Signature & timestamps need to be generated for each API call for e.g . Pagination call Also? YES, for each and every call including pagination , you need to generate new Signature and Timestamps.
Does Authentication need to do for each call? YES, Authentication need to do for each call.
Upvotes: 0
Reputation: 11
In Order to generate multiple parameter pass string as by escaping sting.
Auth Signature & timestamp need to be generated for each API call for e.g . Pagination call Also
Upvotes: 0