laika-framework

Models & Database

Laika’s data layer is laikait/laika-model — a PDO query builder and schema builder supporting MySQL, MariaDB, PostgreSQL, SQLite, SQL Server, Oracle, and Firebird. This page covers how it’s wired into a Laika app; see the laika-model README for the exhaustive API reference (joins, aggregates, transactions, chunking, casts, full schema builder, etc.).

Connections

Connections are configured in lf-config/database.php — each top-level key is a connection name:

return [
    'default' => [
        'driver'   => 'mysql',
        'host'     => 'localhost',
        'port'     => 3306,
        'database' => 'test',
        'username' => 'root',
        'password' => '',
    ],
];

Models resolve the 'default' connection unless told otherwise. Connections are created lazily — nothing connects until a model or schema call actually needs it.

Defining a Model

php laika model:make User --table=users --id=id --uid=uid
namespace App\Model;

use Laika\Model\Model;

class UsersModel extends Model
{
    protected string $table          = 'users';
    protected string $id             = 'id';
    protected string $uid            = 'uid';
    protected string $connection     = 'default';
    protected bool   $softDelete     = false;
    protected string $deletedAtColumn = 'deleted_at';

    /** @var array<string,string> */
    protected array $casts = [
        'id'     => 'int',
        'active' => 'bool',
    ];
}

Basic CRUD

$users = new UsersModel();

// Select
$all    = $users->get();
$active = $users->where(['active' => 1])->get();
$one    = $users->where(['id' => 1])->first();

// Insert — returns the last inserted ID
$id = $users->insert(['name' => 'Alice', 'email' => 'alice@example.com']);

// Update — requires a WHERE clause
$users->where(['id' => $id])->update(['name' => 'Alice Smith']);

// Delete — requires a WHERE clause
$users->where(['id' => $id])->delete();

update() and delete() throw InvalidArgumentException if called without a where() — this is intentional, to prevent accidental full-table mutations.

Defining a Schema

Schemas own table DDL and live in lf-app/Schema, one class per table, extending Laika\Model\Contract\SchemaAbstract:

namespace App\Schema;

use Laika\Model\Schema\Schema;
use Laika\Model\Schema\Blueprint;
use Laika\Model\Contract\SchemaAbstract;

class UsersModelSchema extends SchemaAbstract
{
    protected string $table      = 'users';
    protected string $connection = 'default';

    public function up(): void
    {
        Schema::on($this->connection)->createIfNotExists($this->table, function (Blueprint $t) {
            $t->bigId('id');
            $t->string('uid');
            $t->string('email');
            $t->string('first_name');
            $t->string('last_name');
            $t->timestamp('deleted_at')->nullable()->default(null);

            $t->unique('email');
        });
    }
}

Running Migrations

php laika app:migrate               # every discovered schema
php laika app:migrate --table=UsersModelSchema   # just one

app:migrate discovers every App\Schema class automatically, plus any schema classes shipped by installed packages (e.g. laikait/laika-auth’s auth_tokens table, laikait/laika-queue’s job tables) — no manual wiring needed.

Security

Full Reference

The laika-model README covers everything not repeated here: