Weave Code
Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Laravel Webflow Laravel Package

jeffersongoncalves/laravel-webflow

A Laravel package for integrating Webflow into your application, offering configuration, service bindings, and helpers to fetch and manage Webflow CMS content and API data from within your Laravel projects.

View on GitHub
Deep Wiki
Context7

Getting Started

The package is a thin, opinionated wrapper around Laravel's Http client for the Webflow REST API v2. There is no SDK magic to learn — if you know the Webflow v2 endpoints, you know what the package does.

  1. composer require the package, then publish its config (php artisan vendor:publish --tag=webflow-config or similar — check the README for the exact tag).
  2. Generate a Site API token in Webflow: Site settings → Apps & integrations → API access. Store it as WEBFLOW_TOKEN in .env; never commit it. Token scopes are selected at creation time (cms:read, cms:write, forms:read, sites:read, etc.) — decide these up front, because re-scoping means minting a new token.
  3. If the service provider isn't auto-discovered, register it, and alias the facade in config/app.php.

First use case: a read-only smoke test. Resolve the client (via facade or container), call the sites endpoint, and dump the response. This validates token, network, and package wiring in one shot before you touch CMS data. Then move to listing collections for a site and paginating items in one collection — that's the 80% path for most real integrations.

Implementation Patterns

Wrap the client, don't sprinkle it. Put the package behind your own WebflowService or a small set of repositories. The Webflow API is stable but not static; a single seam means a breaking package upgrade touches one file instead of forty.

Cache collection schemas aggressively. Collection field definitions change rarely and are needed to build forms, map DTOs, and validate payloads. Cache::remember("webflow.collection.{$id}.schema", now()->addDay(), ...) saves a request per operation and keeps you well under rate limits.

Treat CMS writes as two-step. Creating or updating an item does not publish it. You create/update, then publish the item explicitly. Model this in your own API ($service->upsertAndPublish($collection, $data)) so callers can't accidentally leave content in draft — or, if drafts are the point, make that explicit in the method name.

Queue anything bulk. Migrating 2,000 items is a job, not a request. Use a queued job with RateLimited middleware or Redis::throttle, chunk the item list, and make each job idempotent by keying on slug or an external ID you control. Webflow has no upsert-by-external-id, so your job needs a lookup step.

Ingest form submissions via webhook, not polling. Configure a webhook in Webflow pointing at a route in your app, verify and persist the payload, then dispatch. Polling form submissions on a schedule works but burns rate limit and lags. Either way, dedupe on submission ID — webhooks retry.

Test with Http::fake(). The package rides on Laravel's HTTP client, so Http::fake([...]) and Http::assertSent() work as normal. Record real responses once into tests/Fixtures/webflow/*.json and replay them; hand-written fakes drift from the real shape fast, especially for rich-text and reference fields.

Multi-tenant: if you're building for multiple client sites, don't rely on the single configured token. Resolve credentials per tenant (a WebflowAccount model holding an encrypted token) and construct a client instance with that token rather than the singleton from the container.

Gotchas and Tips

  • Rate limits are the number one failure mode. Webflow enforces per-token request limits (on the order of 60 requests/minute for CMS operations) and returns 429. The wrapper likely does not retry for you — add ->retry(3, 200, throw: false) at your seam, or a job-level backoff. A silent 429 inside a loop looks exactly like "the API is broken."
  • Staged vs. live reads. Webflow v2 distinguishes draft/staged content from published content. If items you just created don't appear in a read, you're almost certainly reading the wrong view or haven't published. Confirm which endpoint variant the package calls before debugging anything else.
  • Pagination is offset/limit with a total in the response. Loop until collected >= total and guard against total shifting mid-loop on large, actively-edited collections. Set an explicit limit (100 is the usual max) rather than accepting defaults.
  • 401 vs. 403 means different things. 401 = bad/missing token. 403 = valid token, insufficient scope, or the site isn't accessible to that token. Check scopes before rewriting code.
  • IDs are per-collection, slugs are mutable. Never use a slug as a primary key in your own DB; store the Webflow item ID and treat the slug as a display field. Renaming a slug in Webflow silently orphans slug-keyed records.
  • Rich text fields are large nested JSON, not HTML. Store them as json/longText and render with a dedicated renderer. Naively json_encode-ing an entire item into a log line will flood your logs.
  • Site-wide publish is slow and not obviously idempotent. Batch publishes can take a while and may not be synchronous. Don't put them in a web request; queue and verify.
  • Pin the version. This is a 1.0.0 community wrapper, so treat minor bumps as potentially notable. Read the changelog before composer update, and lock the constraint (^1.0) rather than floating.
  • Extension points to look for: a configurable base URL, a swappable HTTP client (useful for adding default headers, logging, or a tracing middleware), and whether the client is bound as a singleton. If it's a singleton, you must build your own factory for multi-tenant tokens.
  • Log request IDs and endpoint paths on failure. Webflow error bodies are terse; the path and payload shape are usually what tells you which of the ten possible causes you hit.
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
uni-method/symfony-lib
tacticmedia/scim-server-bundle
neika-ai/symfony-bundle
mattleads/agent-publishing-bundle
glavweb/framework-bundle
glavweb/extra-bundle
glavweb/api-bundle
glavweb/admin-bundle
adachsoft/api-version-bundle
elsayed85/laravel-api-exceptions
ouhssini/laravel-demo-mode
daworks/ncloud-outbound-mailer-driver
gp247/cms
ignibyte/aic-gates
nexa-merchant/blog
novasa/laravel-language-center
opencage/geocode
adolfoholzer/parameters
livenetworks/ln-starter
cgv/localized-resource