skip to Main Content

In my server.js file, I register the app/uninstalled webhook inside the afterAuth function like this:

const response = await Shopify.Webhooks.Registry.register({
      shop,
      accessToken,
      path: "/webhooks",
      topic: "APP_UNINSTALLED",
      apiVersion: ApiVersion.October20,
      webhookHandler: (topic, shop, body) => {
        //console.log(topic, shop,body);
        delete ACTIVE_SHOPIFY_SHOPS[shop];
      },
    });

I am listening to route like this

router.post("/webhooks", appUninstallWebhook, async (ctx) => {
try {
  await Shopify.Webhooks.Registry.process(ctx.req, ctx.res);
  console.log(`Webhook processed, returned status code 200`);
} catch (error) {
  console.log(`Failed to process webhook: ${error}`);
}

});

I see the webhook successfully being registered, however when I delete the app running locally on ngrok in my test Shopify store, I do not see that webhook being triggered.

Any help would be really helpful.

3

Answers


  1. Chosen as BEST ANSWER

    Unfortunately, I couldn't get it working but I got a workaround using another approach.

    const response = await registerWebhook({
      shop,
      accessToken,
      address: `${HOST}/webhooks/app/uninstalled`,
      topic: "APP_UNINSTALLED",
      apiVersion: API_VERSION
    });
    

    And then configure the route

    router.post("/webhooks/app/uninstalled", webhook, async (ctx) => {
      try {
        console.log(`Webhook processed, returned status code 200`);
      } catch (error) {
        console.log(`Failed to process webhook: ${error}`);
      }
    });
    

  2. You can try to register APP_UNINSTALLED webhook in /auth/callback route of your shopify app i.e during oauth process register your webhook.

    Sample code:

    app.get('/auth/callback', async (req, res) => {
        try {
            const shopSession = await Shopify.Auth.validateAuthCallback(req, res, req.query);
            const { shop, accessToken } = shopSession;
    
            const response = await Shopify.Webhooks.Registry.register({
                path: '/api/webhooks',
                topic: 'APP_UNINSTALLED',
                accessToken: accessToken,
                shop: shop,
            });
    
            console.log("response", response)
    
            if (!response['APP_UNINSTALLED'].success) {
                console.log(
                    `Failed to register APP_UNINSTALLED webhook: ${response.result}`
                );
            }
    
    
        } catch (error) {
            console.error(error);
        }
    });
    
    app.post("/api/webhooks", async (req, res) => {
        try {
            await Shopify.Webhooks.Registry.process(req, res);
            console.log(`Webhook processed, returned status code 200`);
            res.status(200).send();
        } catch (error) {
            console.log(`Failed to process webhook: ${error}`);
            res.status(500).send(error.message);
        }
    });
    
    
    Login or Signup to reply.
  3. I was able to make it work properly after I noticed the line "app.use(express.json());" was above the webhook definition while it needs to be below of it, according to Shopify instructions.

    app.post('/api/webhooks', async (req, res) => {
        try {
            await Shopify.Webhooks.Registry.process(req, res);
            console.log(`Webhook processed, returned status code 200`);
        } catch (e) {
            console.log(`Failed to process webhook: ${e.message}`);
            if (!res.headersSent) {
                res.status(500).send(e.message);
            }
        }
    });
    
    // And only then...
    app.use(express.json());
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search