Shopify Webhooks work in testing but not in practice - php

I'm having some problems with my Shopify 'orders/paid' webhook that I install onto the users store via the Shopify SDK (using a PHP wrapper: https://github.com/phpclassic/php-shopify). Anyways, I create the webhook like so:
$shop = $this->request->getVar('shop'); // Get Shopify store URL
// Get access token for store
$config = array('ShopUrl' => $shop, 'ApiKey' => 'xxx', 'SharedSecret' => 'xxx');
\PHPShopify\ShopifySDK::config($config);
$accessToken = \PHPShopify\AuthHelper::getAccessToken();
// Keep track of access_token for SDK calls and authenticate to store for webhook creation
$addToken = $this->Stores->addAccessToken($shop, $accessToken);
$config = array('AccessToken' => $accessToken, 'ShopUrl' => $shop);
$shopify = new \PHPShopify\ShopifySDK($config);
// Create orders/paid webhook
$orderPaidHook = array('topic' => 'orders/paid', 'address' => 'https://api.autoloapp.com/webhook/create', 'format' => 'json');
try {
$webhooks = $shopify->Webhook->post($orderPaidHook);
}
This code as far as I can tell works, using print_r($webhooks) gives me a valid Webhook that has (in theory) been installed on to the store. However, when an order is actually paid for on the store I DO NOT get a message.
Using the "Test Webhook" settings under "Notification" in the Shopify Admin my webhook works perfectly. Using PostMan to simulate a webhook call works perfectly.
The code to process the webhook looks like this:
$headers = getallheaders();
$topic = $headers['X-Shopify-Topic'];
$storeName = $headers['X-Shopify-Shop-Domain'];
if ($topic == 'orders/paid') {
// Do some stuff, insert row into database
}
Again, when I use PostMan or the built-in "Test Webhook" setting for Shopify the row in my database gets created just fine. When I do it with a real webhook nothing happens. I'm not sure why this is happening, as far as I know all the headers should be the same. Do I need to verify the webhook in some way?
For reference I'm using CodeIgniter 4.0, PHP 7.0, and the newest version of the Shopify SDK.
I found this note on Shopify's Docs: "Note that if you are using a Rack based framework such as Ruby on Rails or Sinatra the header you are looking for is HTTP_X_SHOPIFY_HMAC_SHA256". With my current set-up I should still be using X-Shopify-Shop-Domain instead of HTTP_X_Shopify_Shop_Domain correct? Any help greatly appreciated!

So I finally figured out that for some reason the 'orders/paid' webhook wouldn't work for me in "production environments" despite working fine in my test environments. Simply changing the topic to 'orders/create' resolved my problem.

Related

Issue when create a user on Azure B2C using Microsoft Graph API

Issue
I'm trying to build a little script PHP to integrate with the Microsoft Graph API.
I have an admin account in Azure, and have set up a new app through the portal. I've downloaded and installed the PHP SDK, and have managed to set everything up so that I can get a user successfully.
However, POSTing a new user returns me a 400 bad request:
$newUser = new User();
$newUser->setAccountEnabled(true);
$newUser->setGivenName('name');
$newUser->setSurname('surname');
$newUser->setUserPrincipalName('email#dot.com');
$password = new PasswordProfile();
$password->setPassword("pwd");
$password->setForceChangePasswordNextSignIn(false);
$newUser->setPasswordProfile($password);
$identities = new ObjectIdentity();
$identities->setSignInType("emailAddress");
$identities->setIssuer("a tenantId");
$identities->setIssuerAssignedId("email#dot.com");
$newUser->setIdentities($identities);
$user = $this->graph->createRequest('POST', '/users')
->attachBody($newUser)
->setReturnType(Model\User::class)
->execute();
Returns:
{"error":{"code":"BadRequest","message":"Property identities in payload has a value that does not match schema.","innerError":{"date":"2021-11-15T15:26:24","request-id":"an id","client-request-id":"an id"}}}
How can I solve this issue?
Thanks for any help.
Update
I have found a solution for this problem (obviously, is temporary).
The section "identities" must be set as an array (in JSON) like in this example
"identities": [
{
"signInType": "emailAddress",
"issuer": "contoso.onmicrosoft.com",
"issuerAssignedId": "jsmith#yahoo.com"
}
]
Probably, the PHP code above not set the section "identities" as an array.
Now, I send directly a JSON with the section "identities" as an array but I would like to use the PHP code above.
How can I transform the PHP code above to pass "identities" as an array like in the JSON example?
Thanks again.
Try creating an array and adding the identities on there like. This will add the identities property as an array of Model\ObjectIdentity()
...
$identities = [];
$identity = new Model\ObjectIdentity();
$identity->setSignInType("type");
$identity->setIssuer("issuer");
$identity->setIssuerAssignedId("issure-assigned-id");
array_push($identities, $identity);
$newUser->setIdentities($identities);
...

Bigcommerce customer login api (single sign-on) invalid login issue

I'm new to bigcommerce and jwt tokens. I'm trying to get the customer login api to work on a trail store. But have not been able to successfully login a customer automatically.
I got it to work once or twice, but now it doesn't work anymore, and an unable to figure out the odd behavior since nothing changed with the code. I've tried googling if anyone else has had issues with the customer login api but have found nothing.
I've gone thru the tutorial on https://developer.bigcommerce.com/api/v2/#customer-login-api and copied the example provided.
Is there something I'm missing with the code below?
I've gone to developer.bigcommerce.com and created a draft app.
I got the Client ID and Client Secret from the draft app.
I've gone into my trial store and successfully installed the draft app.
I've tested this page on SSL as well.
Could it be because it's a trail store and it will only work if it's a real store?
Thanks.
Here is the php code below:
include "vendor/autoload.php";
use Bigcommerce\Api\Client as Bigcommerce;
use Firebase\JWT\JWT;
function getCustomerLoginToken($id, $redirectUrl = '', $requestIp = '') {
/*
if (empty(self::$client_secret)) {
throw new Exception('Cannot sign customer login tokens without a client secret');
}
*/
$payload = array(
'iss' => '#MyApp1's Client ID#',
'iat' => time(),
'jti' => bin2hex(random_bytes(32)),
'operation' => 'customer_login',
'store_hash' => '#Store Hash#',
'customer_id' => $id
);
if (!empty($redirectUrl)) {
$payload['redirect_to'] = $redirectUrl;
}
if (!empty($requestIp)) {
$payload['request_ip'] = $requestIp;
}
return JWT::encode($payload, "#MyApp1's Client Secret#", "HS256");
}
$jwt = getCustomerLoginToken(1);
header("Location: " . 'https://store-#Store Hash#.mybigcommerce.com/login/token/' . $jwt);
exit();
There are a couple of constraints that can cause errors:
The app must be installed on the store (seems like you're all good here - you can also test with an API token created locally in the store - https://support.bigcommerce.com/articles/Public/Store-API-Accounts/)
The app must have the Login OAuth scope
The JWT URL must be visited within about 30 seconds, or it won't work.
The computer/server that's generating the JWT needs to have a clock that's synchronized, otherwise your IAT value will appear to have been created more than 30 seconds ago or even in the future which will fail.
The URL can only be visited exactly once - if anything runs a GET request against it other than the intended end user's browser, it won't work. For example, if you send the URL in a Slack message, slack will try to preview the link by visiting it and therefore invalidate it.
It's good to double-check that your JWT is valid at https://jwt.io/
BigCommerce support has access to logs which can shed more light on the situation if you've ruled out the above.
Hope this helps!
do not need app client_id and Secret code , you need to api's client_id and secret code

Connect to Google AdSense API via PHP

I'm trying to connect to AdSense API using a PHP script.
I started using this tutorial by google: https://developers.google.com/api-client-library/php/start/get_started#build-the-client-object
However, I didn't manage to connect. This is what I've tried:
$client = new Google_Client();
$client->setApplicationName("AppName");
$client->setDeveloperKey(API_Key);
$client->setAuthConfigFile('../AdSense/google-api-php-client/client_secret.json');
$service = new Google_Service_AdSenseTest($client);
$results = $service->testReportsGenerate();
foreach($results as $item)
{
echo $item;
}
And I came across a few problems, the main one is that the code doesn't recognize the "Google_Service_AdSenseTest" class - even though the code suggested it.
So my real question is this: What service should I use if I want to pull data from AdSense? And how do I set the needed parameters (meaning - which dimensions and metrics to get)?
Thank you.
You need to implement OAuth requests as you do for every single google api, (use Phil Sturgeon's OAuth2.0 protocol if you use codeigniter, well implemented.) or any oauth2 client scripts will do.
The google api library is here : https://github.com/googleapis/google-api-php-client-services. Use composer to install these libraries.
The adsense class is here : https://github.com/googleapis/google-api-php-client-services/blob/master/src/Google/Service/AdSense.php
The class/function which makes the request to google must setup an oauth client and specify a redirect url (which in turn must be registered on google api console )
The scopes are
../auth/adsense
../auth/adsense.readonly
Once everything is done, you can make a request.
I implemented it with Codeigniter for searchconsole, adsense and other useful libraries they all works awesome. Besides i connected google sheets as well, so every report is available to me in google sheet as it is needed.
With oAuth Access token, The code :
$client = new Google_Client();
$adsenseService = new Google_Service_AdSense(...);
$client->setApplicationName("Adsense Console");
$client->setDeveloperKey($apiKey);
$client->setAccessToken( $token->access_token );
$params = array('maxResults' => 1000, 'pageToken' => null, 'alt' => 'json', 'fields' => array(), 'prettyPrint' => true, 'quotaUser' => '', 'userIp' => '' );
$accounts = $adsenseService->accounts->listAccounts($params);
//this will print a json array
echo '<pre>' ; print_r($accounts); echo '<pre>'; die();
for adclients,
$adsense->adclients->listAccountsAdclients($params);
The params ref is here,
https://developers.google.com/adsense/management/v1.4/reference/accounts/adclients/list#try-it
you could try the example from https://github.com/googleads/googleads-adsense-examples/tree/master/php-clientlib-1.x/v1.x
More info at https://developers.google.com/adsense/management/getting_started

authorize.net cim empty response array using php sdk without errors

I am getting an empty array response from authorize.net without any errors.
AuthorizeNetCIM_Response Object ( [xml] => [response] => )
I am using the new php sdk. Here is my code
//authorizenet configuration
define("AUTHORIZENET_API_LOGIN_ID",'');
define("AUTHORIZENET_TRANSACTION_KEY",'');
define("AUTHORIZENET_SANDBOX",true);
//Create new customer profile
$request = new AuthorizeNetCIM;
$customerProfile = new AuthorizeNetCustomer;
$customerProfile->description = "Bar Express Customer";
$customerProfile->email = "a97eehdhd#gmail.com";
$response =$request->createCustomerProfile($customerProfile);
if ($response->isOk()) {
$customerProfileId = $response->getCustomerProfileId();
}
echo print_r($response);
Authorize.net is doing some upgrades to their system. You need to go to the latest SDK of authorize.net on github here and download that. Inside the lib/ssl folder, copy the cert.pem file, and paste it in the sdk inside the same folder lib/ssl. Overwrite the existing certificate file. Thats it. It should start working :)
I think you are passing some missing values to create customer profile like :
merchantCustomerId, refId etc.
I think , you are not being connected to authorize.net properly . Please update authorize.net sdk .

Paypal API Returns Access Token as Null

I have installed the Paypal PHP SDK and am having trouble getting a access token in Sandbox mode.
$sdkConfig = array(
"mode" => "sandbox"
);
// new OAuthTokenCredential(ClientID, Secret, sdkConfig)
$cred = new OAuthTokenCredential("$clientID","$secret", $sdkConfig);
The $cred, when returned, only has the client, secret and logging manager populated, everything else is null.
When stepping through the OAuthTokenCredential class it only runs through as far as the initial function. None of the accesstoken functions run.
I'm assuming that the SDK is okay as other people are presumably using it, so I'm guessing that there is a fairly simple solution.
It isn't documented anywhere, but I've found that adding this directly after the above code works perfectly.
$cred->accessToken = $cred->getAccessToken($sdkConfig);
Not sure why it isn't documented, but this now works for me.

Categories