Skip to content

MariaDB databases: step by step

Two Templates do the work, so the CLI and the console produce identical objects. See the overview for why the server belongs to your project and what the two logins are for.

For the same steps in the console, see the console walkthrough.

Create a server

You need at least one. One server holds many databases, so most projects create this once.

oc process -n openshift mariadb-instance \
  -p NAME=mariadb \
  -p NAMESPACE=<project> \
  -p STORAGE_SIZE=5Gi \
  | oc apply -f -

That creates two things: the MariaDB, and a Secret named mariadb-root holding root's generated password.

Watch it come up:

oc get mariadb -n <project> -w

It reports Running with READY True in about a minute on default settings.

Create a database

oc process -n openshift mariadb-database \
  -p NAME=<database> \
  -p NAMESPACE=<project> \
  -p INSTANCE_NAME=mariadb \
  -p DB_USER=<database>-user \
  | oc apply -f -

That creates four objects: the Database, the User your application connects as, a Grant giving that user all privileges on this database only, and a Secret named <database>-db-user with the credentials and the connection details.

The database is created with character set utf8mb4 and collation utf8mb4_unicode_ci. Pass -p CHARACTER_SET=... -p COLLATE=... if you need something else; the two must belong together, and a mismatched pair is rejected by the server rather than by the template.

To see the objects before applying them, drop the pipe:

oc process -n openshift mariadb-database \
  -p NAME=<database> -p NAMESPACE=<project> \
  -p INSTANCE_NAME=mariadb -p DB_USER=<database>-user -o yaml

List

oc get mariadb -n <project>
oc get databases.k8s.mariadb.com,users.k8s.mariadb.com,grants.k8s.mariadb.com -n <project>

oc get databases is ambiguous

PostgreSQL installs a Database kind too, so in a project running both the short form returns whichever the API server resolves first. Use the fully qualified name.

Check a database reached the server:

oc get databases.k8s.mariadb.com <database> -n <project> \
  -o jsonpath='{.status.conditions[?(@.type=="Ready")].status}{"\n"}'

True means the server has it. The User and Grant carry the same condition.

Connect

Everything a workload needs is in the Secret named after the database:

envFrom:
  - secretRef:
      name: <database>-db-user

That gives the container username, password, host, port and database. The host is the server's Service, <server>.<project>.svc.cluster.local, on port 3306.

Change

Grow the server's disk - it can be grown, never shrunk:

oc patch mariadb mariadb -n <project> --type=merge \
  -p '{"spec":{"storage":{"size":"10Gi"}}}'

Add another database - run the database template again with a new NAME and DB_USER against the same INSTANCE_NAME. You do not need a second server.

The database name, the server it lives on, its character set and its collation are all fixed after creation. To change any of them, create a new database and move the data.

Delete

oc delete grants.k8s.mariadb.com <user>-<database> -n <project>
oc delete users.k8s.mariadb.com <user> -n <project>
oc delete databases.k8s.mariadb.com <database> -n <project>
oc delete secret <database>-db-user -n <project>

Deleting the Database object does not drop the database

The template sets spec.cleanupPolicy: Skip, so the data stays on the server, still occupying storage and still holding the name. To drop it when you mean to, set the policy to Delete before deleting the object:

oc patch databases.k8s.mariadb.com <database> -n <project> --type=merge \
  -p '{"spec":{"cleanupPolicy":"Delete"}}'

Take a dump first if you might want the data back:

oc exec -n <project> <server>-0 -- \
  mariadb-dump -u root -p"$(oc get secret <server>-root -n <project> \
    -o jsonpath='{.data.password}' | base64 -d)" <database> > <database>.sql

Deleting the server removes every database on it:

oc delete mariadb <server> -n <project>