MemehCMSDocumentation
Developer guide

Connect your website to MemehCMS

Keep your existing frontend. Fetch published content from the public API using your institution ID. No CMS installation or API token is needed for public reads.

Before you start

  1. Ask an institution admin for the workspace's Institution ID (a UUID on the Headless API screen). If you can access several institutions, choose the correct workspace first.
  2. Publish at least one article or page in that workspace. Drafts do not appear in the public API.
  3. Use https://memehcms.com as the API base for MemehCMS Cloud. Your website can run on any host or framework.

Two ways to build: use the API with your own Laravel, Next.js, Astro, PHP or other server; or download the PHP Web Engine for a ready-to-customize site. You do not need both.

1. Fetch published articles

Replace the UUID with your Institution ID, then run this in a terminal:

export MEMEH_TENANT_ID="YOUR-INSTITUTION-UUID"
curl -fsS --get 'https://memehcms.com/api/articles' \
  --data-urlencode "tenant_id=$MEMEH_TENANT_ID" \
  --data-urlencode 'per_page=3' \
  --data-urlencode 'include=category,feature'

The list response has data (article rows), meta (page and total), and links (next and previous page URLs). An empty data array usually means nothing is published for that institution yet.

{
  "data": [{"title": "Example title", "slug": "example-title", "href": "/articles/example-title", "status": "published"}],
  "meta": {"current_page": 1, "per_page": 3, "total": 1, "last_page": 1},
  "links": {"next": null, "prev": null}
}

Open one article by slug to get its body_html:

curl -fsS --get 'https://memehcms.com/api/articles/example-title' \
  --data-urlencode "tenant_id=$MEMEH_TENANT_ID"

A detail response is {"data": { ... }}. The href value is a suggested path on your website, not a hosted MemehCMS page.

Use a client instead of building requests

The Headless API screen shows the selected workspace's connection details, a searchable endpoint directory, and copyable requests. Sign in as a member of that institution to use it.

These are dependency-free source downloads with setup examples, not npm or Composer registry packages. Both add the Institution ID to every request and preserve the API response envelope.

2. Render it in your frontend

Call the API from your server or build process. Here is a complete Node.js 18+ example that prints article titles:

// articles.mjs
const tenantId = process.env.MEMEH_TENANT_ID;
if (!tenantId) throw new Error('Set MEMEH_TENANT_ID first');

const url = new URL('https://memehcms.com/api/articles');
url.searchParams.set('tenant_id', tenantId);
url.searchParams.set('per_page', '10');

const response = await fetch(url, { headers: { Accept: 'application/json' } });
if (!response.ok) throw new Error(`MemehCMS returned ${response.status}`);

const { data: articles, meta } = await response.json();
for (const article of articles) {
  console.log(`${article.title} -> ${article.href}`);
}
console.log(`Page ${meta.current_page} of ${meta.last_page}`);
MEMEH_TENANT_ID="YOUR-INSTITUTION-UUID" node articles.mjs

Use the slug to make a route on your site, then request /api/articles/{slug}. For pages, use /api/pages and /api/pages/{slug}. Page detail can contain body_html or structured sections; inspect builder.mode and map section types to your components. Escape titles and summaries as text. Only render reviewed body_html as HTML in a deliberate rich-content component with your normal content-security controls.

Browser calls: cross-origin requests require your website origin in the CMS CORS allowlist. Server-side requests work without browser CORS. Do not put admin credentials or private tokens in frontend JavaScript.

4. Go live

  • Store the Institution ID in server-side configuration, not in each component.
  • Keep your public site on HTTPS. Cache successful GET responses and show a controlled fallback if the API is unavailable.
  • Verify published article detail, page detail, menus, and image URLs on the real domain.
  • Check empty states, pagination, 404s, accessibility, and mobile layout.
  • Do not expose the CMS admin session or use the public API as a write API.

When a request fails

ResultCheck
Empty dataConfirm Institution ID, published status, and selected workspace.
404 detailConfirm slug, institution, and that the item is published.
404 menuAssign a menu to the requested location.
422Check that tenant_id is one UUID string, not an array or label.
Browser CORS errorUse a server-side call or ask the platform operator to allowlist your origin.
429Back off and cache responses; the public API is rate-limited.

Need a deployable PHP site instead? Continue with the Web Engine guide.