Project

panda-cms

0.0
There's a lot of open issues
A long-lived project that still receives updates
Better websites on Rails.
2005
2006
2007
2008
2009
2010
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023
2024
2025
 Project Readme

Panda CMS

Caution

This application is being developed in public. It is not ready for production use. If you'd like to try it out (or help with documentation), please contact @jfi by emailing bamboo@pandacms.io.

Panda CMS is the CMS we always wanted. 🐼

Better websites, on Rails.

Read more about the project...

🐼 is grown from our work at Otaina, a small group of freelancers. We needed something that could handle websites large and small – but where we could expand it too. We sent our first websites live in March 2024.

Gem Version Build Status GitHub Last Commit Ruby Code Style

Usage

New applications

To create a new Rails app, run the command below, replacing demo with the name of the application you want to create:

rails new demo $(curl -fsSL https://raw.githubusercontent.com/tastybamboo/generator/main/.railsrc) -m https://raw.githubusercontent.com/tastybamboo/generator/main/template.rb

cd into your directory (e.g. demo), and you'll see rails db:migrate and rails db:seed have already been run for you.

Then run bin/dev. You'll see a basic website has automatically been created for you at http://localhost:3000/

The easiest way for you to get started is to visit http://localhost:3000/admin and login with your GitHub credentials. As the first user, you'll automatically have an administrator account created.

When you're ready to configure further, you can set your own configuration in config/initializers/panda.rb. Make sure to configure your authentication providers and update the domain restriction!

Existing applications

Add the following to Gemfile:

gem "panda-cms"

For initial setup, run:

bundle install
rails generate panda:cms:install
rails panda:cms:install:migrations
rails db:migrate
rails db:seed

You may want to check this does not re-run any of your existing seeds!

If you don't want to use GitHub to login (or are at a URL other than http://localhost:3000/), you'll need to configure authentication providers (in config/initializers/panda.rb), and then set your user's admin attribute to true once you've first tried to login.

Configuration

All Panda configuration is managed in config/initializers/panda.rb. The generator creates this file with sensible defaults including Google OAuth authentication:

# config/initializers/panda.rb
Panda::Core.configure do |config|
  config.admin_path = "/admin"

  config.login_page_title = "Panda Admin"
  config.admin_title = "Panda Admin"

  config.authentication_providers = {
    google_oauth2: {
      enabled: true,
      name: "Google",
      client_id: Rails.application.credentials.dig(:google, :client_id),
      client_secret: Rails.application.credentials.dig(:google, :client_secret),
      options: {
        scope: "email,profile",
        prompt: "select_account",
        hd: "yourdomain.com" # Restrict to specific domain
      }
    }
  }

  # Core settings
  config.session_token_cookie = :panda_session
  config.user_class = "Panda::Core::User"
  config.user_identity_class = "Panda::Core::UserIdentity"
end

Important: Update hd: "yourdomain.com" to your organization's domain to restrict admin access, or remove this line to allow any Google account.

See the Configuration Documentation for detailed information on all available settings.

Engine Mounting

The Panda CMS engine automatically mounts itself via an after_initialize hook. You do not need to manually add mount Panda::CMS::Engine => "/" to your routes file. The engine will:

  • Mount itself at the root path
  • Add admin routes under the configured admin path (e.g., /admin/cms or /manage/cms)
  • Set up a catch-all route for CMS pages (excluding admin paths)

The admin interface structure will be:

  • {admin_path} - Panda Core admin dashboard (authentication, profile)
  • {admin_path}/cms - Panda CMS admin (pages, posts, menus, files)

Styling

Panda CMS does not compile or manage its own CSS. All admin interface styling is provided by Panda Core.

The CMS automatically loads Core's compiled stylesheet:

<link rel="stylesheet" href="/panda-core-assets/panda-core.css">

Core's Rack middleware serves this file from the gem, so:

  • ✅ No CSS copying or compilation needed
  • ✅ Styles update automatically when Core updates
  • ✅ Consistent design across all Panda gems

For details on customizing styles, development workflows, and troubleshooting, see docs/STYLING.md.

For CSS compilation (when contributing to styling), see Panda Core Asset Compilation Guide.

Gotchas

This is a non-exhuastive list (there will be many more):

  • To date, this has only been tested with Rails 7.1, 7.2 and 8
  • There may be conflicts if you're not using Tailwind CSS on the frontend. Please report this.

Contributing

We welcome contributions.

See our Contributing Guidelines

Testing

Panda CMS uses RSpec for testing.

Using Fixtures

We encourage using fixtures for tests instead of factories for consistent test data:

  1. Create fixture files in spec/fixtures named after the model's table (e.g., panda_cms_pages.yml)
  2. Define records with unique names and their attributes
  3. Use helper methods to create test templates with mocked file validation

Example fixture format:

# spec/fixtures/panda_cms_pages.yml
home_page:
  title: "Home"
  path: "/"
  panda_cms_template_id: <%= ActiveRecord::FixtureSet.identify(:page_template) %>
  status: "active"
  created_at: <%= Time.current %>
  updated_at: <%= Time.current %>

Example test using fixtures:

# Access fixture using table name and record name
page = panda_cms_pages(:home_page)
expect(page.title).to eq("Home")

When testing models with file validations or complex callbacks, use the helper methods in spec/models/panda/cms/page_spec.rb as a reference.

License

The gem is available as open source under the terms of the BSD-3-Clause License.

Copyright © 2024 - 2025, Otaina Limited.