matheen ulla
matheen ulla

Reputation: 558

Missing required parameters OAuth API (netsuite)

enter code hereI just started working with OAuth1 API's calling from php using GuzzleHttp\Client. In postman it's working fine.In netsuite log file I can see only required parameters is missing. I'm not understanding where I'm going wrong. whenever I'm calling the API I'm getting response as

 #message: """
    Client error: `GET https://7085372.suitetalk.api.netsuite.com/services/rest/record/v1/customer/` resulted in a `400 Bad Request` response:
    {"type":"https://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html#sec10.4.1","title":"Bad Request","status":400,"o:errorD (truncated...)
    """
  #code: 400

php code

$realm = 'xxxxxxx';
$consumer_key = 'xxxxxxxxx';
$oauth_token = 'xxxxxxxxxxxxx';
$oauth_signature_method = 'HMAC-SHA256';
$oauth_version = '1.0';
$consumer_secret = 'xxxxxxxxxxxxx';
$token_secrect = 'xxxxxxxxxxxxx';
$timeStamp = Carbon::now()->timestamp;
$oauth_none = Str::random(11);

$base = 'GET' . "&" . urlencode('https://7085372.suitetalk.api.netsuite.com/services/rest/record/v1/customer/') . "&" . urlencode("oauth_consumer_key=" . urlencode($consumer_key) . "&oauth_nonce=" . urlencode($oauth_none) . "&oauth_signature_method=" . urlencode($oauth_signature_method) . "&oauth_timestamp=" . urlencode($timeStamp) . "&oauth_token=" . urlencode($oauth_token) . "&oauth_version=" . urlencode($oauth_version) . "&realm=" . urlencode($realm));

$key = urlencode($consumer_secret) . "&" . urlencode($token_secrect);
$oauth_signature = base64_encode(hash_hmac('sha256', $base, $key, true));



$authorization = 'OAuth oauth_consumer_key=' . $consumer_key . ',oauth_nonce=' . $oauth_none . ',oauth_signature_method=' . $oauth_signature_method . ',oauth_timestamp=' . $timeStamp . ',oauth_token=' . $oauth_token . ',oauth_version=' . $oauth_version . ',realm=' . $realm . ',oauth_signature=' . $oauth_signature . '';


        try {
            $client = new Client();
            $headers = [
                'Authorization' => $authorization,
                'Content-Type' => 'application/json',
                'Cookie' => 'NS_ROUTING_VERSION=LAGGING'
            ];
            $body = '';

            $request = new Request('GET', 'https://7085372.suitetalk.api.netsuite.com/services/rest/record/v1/customer/', $headers, $body);
            $res = $client->sendAsync($request)->wait();
            dd('here', $res, $res->getBody());
        } catch (RequestException $e) {
            dd($e->getResponse(), $e);
        }

Postman Collection

Upvotes: 0

Views: 748

Answers (1)

José Carlos PHP
José Carlos PHP

Reputation: 1492

In this line:

$base = 'GET' . "&" . urlencode('https://7085372.suitetalk.api.netsuite.com/services/rest/record/v1/customer/') . "&" . urlencode("oauth_consumer_key=" . urlencode($consumer_key) . "&oauth_nonce=" . urlencode($oauth_none) . "&oauth_signature_method=" . urlencode($oauth_signature_method) . "&oauth_timestamp=" . urlencode($timeStamp) . "&oauth_token=" . urlencode($oauth_token) . "&oauth_version=" . urlencode($oauth_version) . "&realm=" . urlencode($realm));

From urlencode("oauth_consumer_key=" . to "&realm=" . urlencode($realm));, you are url_encoding twice, and you are url_encoding = symbols. So your $authorization string is absolutely malformed, and it results in missing parameters.

This can occurs when you write such a long line, and it's difficult to see. It's better to write it down this way:

$base = 'GET&' . urlencode('https://7085372.suitetalk.api.netsuite.com/services/rest/record/v1/customer/')
    . '&oauth_consumer_key=' . urlencode($consumer_key)
    . '&oauth_nonce=' . urlencode($oauth_none)
    . '&oauth_signature_method=' . urlencode($oauth_signature_method)
    . '&oauth_timestamp=' . urlencode($timeStamp)
    . '&oauth_token=' . urlencode($oauth_token)
    . '&oauth_version=' . urlencode($oauth_version)
    . '&realm=' . urlencode($realm);

But it's even better to use an array and http_build_query() function, this way:

$url = 'https://7085372.suitetalk.api.netsuite.com/services/rest/record/v1/customer/';

$data = array(
    'oauth_consumer_key' => $consumer_key,
    'oauth_nonce' => $oauth_none,
    'oauth_signature_method' => $oauth_signature_method,
    'oauth_timestamp' => $timeStamp,
    'oauth_token' => $oauth_token,
    'oauth_version' => $oauth_version,
    'realm' => $realm,
);

$base = 'GET&' . urlencode($url) . '&' . http_build_query($data);

Note.- Also, it's a good idea to use a variable for the url, since you are using it more than 1 time.

However, maybe there are more issues left. I'm not sure if you are are doing well the request.

And it's a good idea to have a function to generate OAuth signature.

Here you are a remaking of your code:

$url = 'https://7085372.suitetalk.api.netsuite.com/services/rest/record/v1/customer/';
$consumer_secret = 'xxxxxxxxxx';
$token_secret = 'xxxxxxxxxx';
$data = array(
    'oauth_consumer_key' => 'xxxxxxxxxx',
    'oauth_nonce' => Str::random(11),
    'oauth_signature_method' => 'HMAC-SHA256',
    'oauth_timestamp' => Carbon::now()->timestamp,
    'oauth_token' => 'xxxxxxxxxx',
    'oauth_version' => '1.0',
    'realm' => 'xxxxxxxxxx',
);

$oauth_signature = generateOauthSignature(
    'GET',
    $url,
    $data['oauth_consumer_key'],
    $data['oauth_nonce'],
    $data['oauth_signature_method'],
    $data['oauth_timestamp'],
    $data['outh_version'],
    $consumer_secret,
    $token_secret,
    $data['oauth_token'],
    array('realm' => $data['realm']),
);
$authorization = 'OAuth ';
foreach ($data as $key => $val) {
    $authorization .= ',' . $key . '=' . $val;
}
$authorization .= ',oauth_signature=' . $oauth_signature;

try {
    $client = new Client();
    $headers = [
        'Authorization' => $authorization,
        'Content-Type' => 'application/json',
        'Cookie' => 'NS_ROUTING_VERSION=LAGGING'
    ];
    $body = '';

    $request = new Request('GET', $url, $headers, $body);
    $res = $client->sendAsync($request)->wait();
    dd('here', $res, $res->getBody());
} catch (RequestException $e) {
    dd($e->getResponse(), $e);
}


function generateOauthSignature($method, $url, $consumerKey, $nonce, $signatureMethod, $timestamp, $version, $consumerSecret, $tokenSecret, $tokenValue, $extraParams = array())
{
    $base = strtoupper($method) . "&" . rawurlencode($url) . "&"
        . rawurlencode("oauth_consumer_key=" . $consumerKey
        . "&oauth_nonce=" . $nonce
        . "&oauth_signature_method=" . $signatureMethod
        . "&oauth_timestamp=" . $timestamp
        . "&oauth_token=" . $tokenValue
        . "&oauth_version=" . $version);

        if (!empty($extraParams)) {
            $base .= rawurlencode("&" . http_build_query($extraParams));
        }

    $key = rawurlencode($consumerSecret) . '&' . rawurlencode($tokenSecret);
    $signature = base64_encode(hash_hmac('sha1', $base, $key, true));

    return rawurlencode($signature);
}

Upvotes: 1

Related Questions