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

Inconsistency between listWebhook() function and get request directly from Postman #117

Closed
antoineross opened this issue Aug 17, 2024 · 3 comments

Comments

@antoineross
Copy link

Hi, so I was using the repository: https://github.com/lmsqueezy/nextjs-billing/ and specifically in the code from file: https://github.com/lmsqueezy/nextjs-billing/blob/main/src/app/actions.ts, where we call listWebhooks() I get a different response vs getting the request directly using Postman.

I tested this because I was trying to look for the webhook I created with id #25098 (using the same file from nextjs-billing repo). If you will look at the logs, you will notice that #24749 exists on the logs for both listWebhooks() and using Postman, but the problem lies in #25098 existing in Postman but not in listWebhooks().

To give you more context here is the code I am using:

Code:

export async function hasWebhook() {
  configureLemonSqueezy();

  if (!process.env.WEBHOOK_URL || !process.env.LEMONSQUEEZY_STORE_ID) {
    throw new Error(
      `Missing required env variable(s): ${!process.env.WEBHOOK_URL ? 'WEBHOOK_URL' : ''} ${!process.env.LEMONSQUEEZY_STORE_ID ? 'LEMONSQUEEZY_STORE_ID' : ''}. Please, set them in your .env file.`
    );
  }

  // Check if a webhook exists on Lemon Squeezy.
  const allWebhooks = await listWebhooks({
    filter: { storeId: process.env.LEMONSQUEEZY_STORE_ID },
  });

  console.log("Lemon Squeezy Store ID:", process.env.LEMONSQUEEZY_STORE_ID);
  console.log("allWebhooks.data", allWebhooks.data?.data);
}

  return allWebhooks;

I get the following results from logs:

Lemon Squeezy Store ID: 54500
allWebhooks {
  meta: {
    page: {
      currentPage: 1,
      from: 1,
      lastPage: 1,
      perPage: 10,
      to: 1,
      total: 1
    }
  },
  jsonapi: { version: '1.0' },
  links: {
    first: 'https://api.lemonsqueezy.com/v1/webhooks?filter%5Bstore_id%5D=54500&include=&page%5Bnumber%5D=1&page%5Bsize%5D=10&sort=-createdAt',
    last: 'https://api.lemonsqueezy.com/v1/webhooks?filter%5Bstore_id%5D=54500&include=&page%5Bnumber%5D=1&page%5Bsize%5D=10&sort=-createdAt'
  },
  data: [
    {
      type: 'webhooks',
      id: '24749',
      attributes: [Object],
      relationships: [Object],
      links: [Object]
    }
  ]
}
allWebhooks.data [
  {
    type: 'webhooks',
    id: '24749',
    attributes: {
      store_id: 54500,
      url: '',
      events: null,
      last_sent_at: null,
      created_at: '2024-08-11T14:48:58.000000Z',
      updated_at: '2024-08-11T14:48:58.000000Z',
      test_mode: true
    },
    relationships: { store: [Object] },
    links: { self: 'https://api.lemonsqueezy.com/v1/webhooks/24749' }
  }
]

I have also tried removing the filter but still nothing:

const allWebhooks = await listWebhooks();

But when I call it directly using Postman, I get a different response:

Screenshot 2024-08-17 at 2 49 09 PM

I will also attach a full response here:

{
    "meta": {
        "page": {
            "currentPage": 1,
            "from": 1,
            "lastPage": 1,
            "perPage": 10,
            "to": 2,
            "total": 2
        }
    },
    "jsonapi": {
        "version": "1.0"
    },
    "links": {
        "first": "https://api.lemonsqueezy.com/v1/webhooks?filter%5Bstore_id%5D=54500&page%5Bnumber%5D=1&page%5Bsize%5D=10&sort=-createdAt",
        "last": "https://api.lemonsqueezy.com/v1/webhooks?filter%5Bstore_id%5D=54500&page%5Bnumber%5D=1&page%5Bsize%5D=10&sort=-createdAt"
    },
    "data": [
        {
            "type": "webhooks",
            "id": "25098",
            "attributes": {
                "store_id": 54500,
                "url": "https://0f63-152-32-96-40.ngrok-free.app/api/webhooks/lemonsqueezy",
                "events": [
                    "subscription_created",
                    "subscription_expired",
                    "subscription_updated"
                ],
                "last_sent_at": null,
                "created_at": "2024-08-17T06:28:42.000000Z",
                "updated_at": "2024-08-17T06:28:42.000000Z",
                "test_mode": true
            },
            "relationships": {
                "store": {
                    "links": {
                        "related": "https://api.lemonsqueezy.com/v1/webhooks/25098/store",
                        "self": "https://api.lemonsqueezy.com/v1/webhooks/25098/relationships/store"
                    }
                }
            },
            "links": {
                "self": "https://api.lemonsqueezy.com/v1/webhooks/25098"
            }
        },
        {
            "type": "webhooks",
            "id": "24749",
            "attributes": {
                "store_id": 54500,
                "url": "",
                "events": null,
                "last_sent_at": null,
                "created_at": "2024-08-11T14:48:58.000000Z",
                "updated_at": "2024-08-11T14:48:58.000000Z",
                "test_mode": true
            },
            "relationships": {
                "store": {
                    "links": {
                        "related": "https://api.lemonsqueezy.com/v1/webhooks/24749/store",
                        "self": "https://api.lemonsqueezy.com/v1/webhooks/24749/relationships/store"
                    }
                }
            },
            "links": {
                "self": "https://api.lemonsqueezy.com/v1/webhooks/24749"
            }
        }
    ]
}
@antoineross
Copy link
Author

antoineross commented Aug 17, 2024

Edit: I tried fetching it directly and it returned the list of webhooks properly including id #25098. Is there anything wrong with the way I was calling listWebhooks?

Code:

export async function hasWebhook() {
  if (!process.env.WEBHOOK_URL || !process.env.LEMONSQUEEZY_STORE_ID || !process.env.LEMONSQUEEZY_API_KEY) {
    throw new Error(
      `Missing required env variable(s): ${!process.env.WEBHOOK_URL ? 'WEBHOOK_URL' : ''} ${!process.env.LEMONSQUEEZY_STORE_ID ? 'LEMONSQUEEZY_STORE_ID' : ''} ${!process.env.LEMONSQUEEZY_API_KEY ? 'LEMONSQUEEZY_API_KEY' : ''}. Please, set them in your .env file.`
    );
  }

  const url = `https://api.lemonsqueezy.com/v1/webhooks?filter[store_id]=${process.env.LEMONSQUEEZY_STORE_ID}`;
  
  const response = await fetch(url, {
    method: 'GET',
    headers: {
      'Accept': 'application/vnd.api+json',
      'Content-Type': 'application/vnd.api+json',
      'Authorization': `Bearer ${process.env.LEMONSQUEEZY_API_KEY}`
    }
  });

  if (!response.ok) {
    throw new Error(`HTTP error! status: ${response.status}`);
  }

  const data = await response.json();

  console.log("Lemon Squeezy Store ID:", process.env.LEMONSQUEEZY_STORE_ID);
  console.log("Webhooks data:", data);

  // Check if WEBHOOK_URL ends with a slash. If not, add it.
  let webhookUrl = process.env.WEBHOOK_URL;
  if (!webhookUrl.endsWith("/")) {
    webhookUrl += "/";
  }
  webhookUrl += "api/webhooks/lemonsqueezy";

  // Find the specific webhook we're looking for
  const webhook = data.data.find(
    (wh: any) => wh.attributes.url === webhookUrl && wh.attributes.test_mode
  );

  console.log("Matching Webhook:", webhook);

  return webhook;
}

Logs:

Lemon Squeezy Store ID: 54500
Webhooks data: {
  meta: {
    page: {
      currentPage: 1,
      from: 1,
      lastPage: 1,
      perPage: 10,
      to: 2,
      total: 2
    }
  },
  jsonapi: { version: '1.0' },
  links: {
    first: 'https://api.lemonsqueezy.com/v1/webhooks?filter%5Bstore_id%5D=54500&page%5Bnumber%5D=1&page%5Bsize%5D=10&sort=-createdAt',
    last: 'https://api.lemonsqueezy.com/v1/webhooks?filter%5Bstore_id%5D=54500&page%5Bnumber%5D=1&page%5Bsize%5D=10&sort=-createdAt'
  },
  data: [
    {
      type: 'webhooks',
      id: '25098',
      attributes: [Object],
      relationships: [Object],
      links: [Object]
    },
    {
      type: 'webhooks',
      id: '24749',
      attributes: [Object],
      relationships: [Object],
      links: [Object]
    }
  ]
}
Matching Webhook: {
  type: 'webhooks',
  id: '25098',
  attributes: {
    store_id: 54500,
    url: 'https://0f63-152-32-96-40.ngrok-free.app/api/webhooks/lemonsqueezy',
    events: [
      'subscription_created',
      'subscription_expired',
      'subscription_updated'
    ],
    last_sent_at: null,
    created_at: '2024-08-17T06:28:42.000000Z',
    updated_at: '2024-08-17T06:28:42.000000Z',
    test_mode: true
  },
  relationships: { store: { links: [Object] } },
  links: { self: 'https://api.lemonsqueezy.com/v1/webhooks/25098' }
}
hasWh true

@brankoconjic
Copy link
Collaborator

brankoconjic commented Aug 17, 2024

Hey @antoineross,

Make sure the API keys are identical and correspond to the same mode (Test or Live). Also, check if the page, layout, or fetch call are cached in Next.js (based on your configuration).

In our example we have added: export const dynamic = "force-dynamic"; to make sure the page is not cached.

See Next.js docs on this.

Edit: I was able to replicate this is on my side.

Add revalidatePath('/'); to hasWebhook function to revalidate the cache in the server action and add export const revalidate = 0; in your page.tsx.

See here.

@antoineross
Copy link
Author

I found that it was a caching issue on my side as well. Deleting /.next fixed it.

Will close this now, thank you for validating the issue. I appreciate it.

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

2 participants