Gs
Applications AWS

Gibbon School MIS 30.0.01 on AWS User Guide

| Product: Gibbon School MIS 30.0.01 on Ubuntu 24.04 on AWS

Overview

This guide covers launching and using Gibbon School MIS 30.0.01 on Ubuntu 24.04 from cloudimg on Amazon EC2. It is one version of the cloudimg Hardened Moodle & E-Learning Platforms AMIs listing on AWS Marketplace; you pick it as the software version when you subscribe and launch. The other learning platforms in the listing are described on the listing's guide hub.

Gibbon is a free and open source school management platform for teachers, students, parents and school leaders. One web application covers student records and enrolment, the timetable and course catalogue, attendance by day and by period, the teacher markbook and reports, behaviour and pastoral care, a school calendar and student alerts, planners and homework, admissions, library, finance and billing, staff records, and a portal where parents and students follow their own timetables, grades and attendance. Gibbon is published under the GNU General Public License version 3. Gibbon is a trademark of its respective owner; cloudimg is not affiliated with, endorsed by, or sponsored by Gibbon Education Ltd. This image packages the upstream open source release together with cloudimg's provisioning, hardening and support.

What is included:

  • Gibbon v30.0.01, served from /var/www/gibbon
  • PHP 8.3 behind Apache 2.4 (mod_php), reachable at https://<instance-address>/; port 80 only ever redirects to HTTPS and serves no content of its own
  • A local MySQL 8.0 database, bound to 127.0.0.1 only
  • A per-instance administrator password, database password, installation id and HTTPS certificate, all generated on first boot. No default, shared or published credential ships in the image
  • The database is created from the command line on the instance's first boot (from Gibbon's own schema, which seeds no user), and Gibbon's setup wizard is blocked outright, so there is no route for a stranger to claim your school
  • Password reset and notification links always point at this instance's own address, never at a hostname supplied by a browser
  • No demo or sample school data, so you start from a clean system
  • 24/7 cloudimg support

Security posture

  • No default login. The administrator password, the MySQL application-role password and the installation id are created on each instance's first boot; none is in the image and no two instances share one. There is exactly one account in the database (the administrator); Gibbon ships no seeded user. MySQL's root@localhost uses socket (peer) authentication with no stored password, and the application role is reachable only over loopback.
  • The setup wizard is dead. Gibbon's three-step installer/install.php is unauthenticated and has no "already installed" guard. The database is therefore created by a command-line script on the instance's first boot, and Apache denies the installer by directory, by location and by filename. A GET or POST to any spelling of the installer returns 403, even with the database empty.
  • Fails closed. Apache is held shut by a drop-in until first boot has minted this instance's secrets and certificate, so a half-provisioned instance stays down rather than open.
  • Only the web tier faces the network. The listening set is exactly 22, 80 and 443. MySQL (3306) listens on 127.0.0.1 only, the MySQL X protocol is disabled, and PHP runs in-process under Apache.
  • The site address comes from configuration, never from the request. On every boot gibbon-baseurl.service sets Gibbon's absolute URL, Apache's server name and the certificate from /etc/cloudimg/gibbon-hostname if set, otherwise from IMDSv2 (public DNS name, else public IPv4, else private IPv4). Apache answers only that name and refuses any other Host, so a forged Host or X-Forwarded-Host cannot steer the links Gibbon builds into reset and notification mail.
  • Real client addresses. mod_remoteip is not loaded and the client-supplied X-Forwarded-For / X-Real-IP / Forwarded headers are stripped, so a forged header cannot make a remote caller look local.
  • No instance metadata access for the web application. Gibbon can be asked to fetch remote URLs (RSS/news feeds, LTI, Google and Microsoft sign-in, the payment gateways, CSV/photo/data imports), so apache2.service and mysql.service are blocked from the instance metadata endpoints (169.254.169.254, the Azure wire-server, and the IPv6 and IPv4-mapped forms). Only the first-boot and base-URL units read metadata, once, for the site address.
  • IMDSv2 required. The AMI is registered with ImdsSupport v2.0, so instances refuse token-less (IMDSv1) metadata requests.
  • Key-only SSH. Password and keyboard-interactive logins, root login and X11 forwarding are off in /etc/ssh/sshd_config.d/00-cloudimg.conf; you sign in as ubuntu with your EC2 key pair.
  • Per-instance identity. SSH host keys, the machine id, the HTTPS certificate and MySQL's server uuid and RSA key pair are all generated fresh on each instance's first boot.
  • Patched at build time. The image is a full apt full-upgrade with all security updates, including PHP 8.3 at the USN-8948-1 build that fixes the "PHP2Shell" RCEs (CVE-2026-109618 / CVE-2026-109619), and Gibbon's vendored PHP libraries are patched to the latest release their own constraints allow (see Security recommendations for the two documented residual advisories).

Prerequisites

  • An AWS account where you can subscribe to AWS Marketplace products and launch EC2 instances
  • An EC2 key pair in the target Region
  • A VPC and subnet, with a public IP address on the instance if your users reach it over the internet
  • A security group that allows 22/tcp from your management network, and 80/tcp and 443/tcp from your users' networks. No other port is needed; do not open 3306

Recommended instance type: m5.large (2 vCPU, 8 GiB RAM). It comfortably serves a single school; use m5.xlarge or larger for a large student body, many teachers taking registers or entering marks at once, or heavy report runs.

Step 1: Launch from AWS Marketplace

  1. Open the Hardened Moodle & E-Learning Platforms AMIs listing by cloudimg and choose View purchase options, then subscribe.
  2. Choose Continue to Configuration. Under Software version choose Gibbon School MIS 30.0.01 on Ubuntu 24.04, pick your Region, and choose Continue to Launch.
  3. Under Choose Action select Launch through EC2.
  4. Set the instance type to m5.large, choose your key pair, and use the seller's security group settings (ports 22, 80 and 443), narrowing port 22 to your management network.
  5. Launch. First boot finishes within two to three minutes.

Step 2: Launch from the AWS CLI

Workstation commands. Replace <ami-id> with the AMI ID shown for the Gibbon School MIS 30.0.01 on Ubuntu 24.04 software version on the listing's launch page, and use your own VPC, subnet, key pair and address ranges.

aws ec2 create-security-group --group-name gibbon-sg \
  --description "Gibbon School MIS" --vpc-id <vpc-id>
aws ec2 authorize-security-group-ingress --group-id <security-group-id> \
  --protocol tcp --port 22 --cidr <your-ip>/32
aws ec2 authorize-security-group-ingress --group-id <security-group-id> \
  --protocol tcp --port 80 --cidr <users-cidr>
aws ec2 authorize-security-group-ingress --group-id <security-group-id> \
  --protocol tcp --port 443 --cidr <users-cidr>

aws ec2 run-instances --image-id <ami-id> --instance-type m5.large \
  --key-name <key-name> --subnet-id <subnet-id> \
  --security-group-ids <security-group-id> --associate-public-ip-address \
  --metadata-options HttpTokens=required \
  --tag-specifications 'ResourceType=instance,Tags=[{Key=Name,Value=gibbon}]'

aws ec2 describe-instances --instance-ids <instance-id> \
  --query "Reservations[].Instances[].[PublicDnsName,PublicIpAddress]" --output text

Step 3: Connect over SSH

ssh -i <key.pem> ubuntu@<public-dns>

The login user is ubuntu.

Step 4: Retrieve your credentials

First boot writes your instance's credentials to a root-only file:

sudo cat /root/gibbon-credentials.txt

It looks like this (your values differ):

gibbon.admin.user=admin
gibbon.admin.pass=<generated-per-instance>
gibbon.db.name=gibbon
gibbon.db.user=gibbon
gibbon.db.pass=<generated-per-instance>

The site address is written to /var/lib/cloudimg/gibbon-address. First boot takes it from /etc/cloudimg/gibbon-hostname if that file exists, otherwise from IMDSv2: the instance's public DNS name, else its public IPv4 address, else its private IPv4 address. If you keep credentials centrally, copy them into AWS Secrets Manager; the MySQL application-role password is also mirrored into Gibbon's own config.php (readable only by root and the web server).

Step 5: Verify the services

systemctl is-active mysql apache2 gibbon-baseurl
ls /var/lib/cloudimg/gibbon-firstboot.done

All three services print active, and the first-boot marker exists (first boot runs once; after a reboot its unit shows as skipped, which is expected). Only 22, 80 and 443 listen on a public address; MySQL is on localhost:

sudo ss -Hltn | awk '{print $4}' | sort -u

The HTTPS front end answers 200, and port 80 redirects to HTTPS on the same name:

SITE=$(cat /var/lib/cloudimg/gibbon-address)
curl -sk -o /dev/null -w "%{http_code}\n" "https://${SITE}/index.php"
curl -s  -o /dev/null -w "%{http_code} %{redirect_url}\n" "http://${SITE}/index.php"

MySQL's root uses socket authentication with no password, and the database is reached only over loopback:

sudo mysql -N -e "SELECT user, host, plugin FROM mysql.user WHERE user IN ('root','gibbon');"

The web application cannot reach the instance metadata service. This runs the same request from inside apache2.service and from your shell; the first fails (blocked), the second returns a token:

CG=$(systemctl show -p ControlGroup --value apache2.service)
sudo bash -c "echo \$\$ > /sys/fs/cgroup${CG}/cgroup.procs; exec curl -s -m 5 -o /dev/null -w '%{http_code}\n' -X PUT -H 'X-aws-ec2-metadata-token-ttl-seconds: 60' http://169.254.169.254/latest/api/token"
curl -s -m 5 -o /dev/null -w '%{http_code}\n' -X PUT -H 'X-aws-ec2-metadata-token-ttl-seconds: 60' http://169.254.169.254/latest/api/token

Step 6: Sign in

Browse to https://<instance-address>/ and sign in as admin with the password from /root/gibbon-credentials.txt. The certificate is self-signed per instance, so your browser warns once; Step 11 installs a trusted certificate. Change the administrator password after the first sign in (User menu, then Preferences).

The Gibbon sign-in page served over HTTPS

After signing in you land on the Gibbon dashboard:

The Gibbon dashboard after signing in

Step 7: Set up your school

Gibbon starts clean, with no demo data. From the administrator account, open School Admin to enter your school's name, year groups, roll groups, departments and the school year calendar, then User Admin to add staff, students and parents (individually or by CSV import). The sign-in page is served over HTTPS from first boot.

Managing users in User Admin

Configuring houses under School Admin

Step 8: Why the setup wizard is blocked

A stock Gibbon exposes installer/install.php, a three-step wizard that writes config.php and creates the first administrator. It has no guard against being run a second time, so anyone who reached it could point your Gibbon at their own database or create their own administrator. On this image the database is created from the command line on first boot and Apache denies the installer outright: every spelling returns 403, and the denial holds even with config.php moved aside and MySQL stopped. You never run the wizard.

Step 9: The failed sign-in lockout

Gibbon locks an account after three consecutive failed sign-ins and then refuses even the correct password until the lock is cleared. If you lock yourself out, clear the counter from the instance:

sudo mysql -D gibbon -e "UPDATE gibbonPerson SET failCount=0 WHERE username='admin';"

Step 10: Use your own hostname

By default the instance serves on its EC2 address. To serve on your own DNS name, point the name at the instance and run:

sudo gibbon-set-hostname school.example.com

This rewrites Gibbon's absolute URL, Apache's server name and the certificate, and persists across reboots. Gibbon then answers only that name (plus the instance's own addresses) and builds all reset and notification links from it.

Step 11: Install a trusted certificate

The per-instance certificate is self-signed. Once the instance serves on a public DNS name you control, install a trusted certificate with Certbot:

sudo snap install --classic certbot
sudo certbot --apache -d school.example.com

Certbot writes the Apache vhost and sets up automatic renewal. Keep 443 reachable from the internet for the HTTP-01 challenge.

Step 12: Outbound email

Gibbon sends password-reset and notification mail. Configure an SMTP relay under System Admin → Third Party Settings → Mail, using a provider such as Amazon SES with SMTP credentials. Because the site address is pinned to this instance, the links in that mail always point back at your Gibbon.

Step 13: Server components

Component Version Notes
Gibbon School MIS 30.0.01 /var/www/gibbon, root-owned, read-only to the web server
PHP 8.3 mod_php under Apache (mpm_prefork)
Apache 2.4 HTTPS vhost + a default reject vhost for unknown Host
MySQL 8.0 127.0.0.1 only, X protocol off, root socket-auth

PHP runs as mod_php, not PHP-FPM, on purpose: several Gibbon module paths contain a space, which PHP-FPM mangles.

Step 14: Filesystem layout

Path Purpose
/var/www/gibbon Application code (read-only to the web server)
/var/www/gibbon/uploads The only writable tree (web-server owned); scripts there are never executed
/var/www/gibbon/config.php Database connection and installation id (0640 root:www-data)
/root/gibbon-credentials.txt Per-instance credentials (root only), written on first boot
/etc/cloudimg/gibbon-hostname Your configured DNS name, if set
/var/lib/cloudimg/gibbon-address The address currently served

Step 15: Managing the services

sudo systemctl restart apache2     # web tier
sudo systemctl restart mysql       # database
sudo journalctl -u apache2 -e      # web logs
sudo journalctl -u gibbon-firstboot # first-boot log

Step 16: Backups

Back up the database and the uploads tree:

sudo mysqldump --single-transaction --default-character-set=utf8mb4 gibbon \
  | gzip > /var/backups/gibbon-$(date +%F).sql.gz
sudo tar czf /var/backups/gibbon-uploads-$(date +%F).tar.gz -C /var/www/gibbon uploads

The dump holds your school's records and the stored password hashes, and both files are created world-readable, so make them root-only straight away with sudo chmod 600 /var/backups/gibbon-*. Copy both off the instance (for example to Amazon S3) and take EBS snapshots on a schedule. To restore, load the SQL dump into the gibbon database and unpack the uploads archive (tested on this image: the dump of a fresh instance is about 90 KB compressed and restores all 208 Gibbon tables).

Step 17: Troubleshooting

  • Browser certificate warning: expected until Step 11 installs a trusted certificate.
  • Locked out after failed sign-ins: clear the counter as in Step 9.
  • Site shows the wrong address in emails: set your DNS name with gibbon-set-hostname (Step 10).
  • Site is down right after launch: first boot has not finished; wait two to three minutes, then check sudo journalctl -u gibbon-firstboot.

Step 18: Security recommendations

  • Restrict 22/tcp to your management network and front the instance with your own DNS name and a trusted certificate (Steps 10-11).
  • Change the administrator password after the first sign in and create named accounts for staff rather than sharing the administrator.
  • Keep the instance patched: sudo apt update && sudo apt full-upgrade.
  • Known residual advisories. Gibbon's vendored PHP libraries are patched to the latest release each library's own composer.json constraint allows. Two advisories have no fix available within those constraints and are reachable only by an authenticated administrator, never by students, parents or the public:
  • firebase/php-jwt CVE-2025-45769 — pinned to the 6.x line by google/apiclient (^2.2). It is only on the code path when an administrator configures Google sign-in.
  • symfony/yaml CVE-2026-109413 / CVE-2026-45304 / CVE-2026-45305 / CVE-2026-45133 (parser resource-exhaustion) — Gibbon requires the 3.x line, and the fix is only in 5.x. Gibbon parses YAML only from files shipped with the application or supplied by an administrator, never from student, parent or public input.

Both are tracked and will be adopted once Gibbon's upstream widens the constraints.

Step 19: Support and licensing

Gibbon is free software under the GNU General Public License version 3; its source is published by Gibbon Education Ltd. cloudimg packages the upstream release with the provisioning and hardening described here and provides 24/7 support for this image by email and live chat: support@cloudimg.co.uk.