---
title: "Introduction"
description: "Specialized PHP data containers, from simple bags to stores validated with JSON Schema, with a common interface and typed getters"
type: "docs"
category: "doc"
tags: []
authors: [Anonymous]
date: "2026-10-20"
last_update: "2026-10-20"
time_minutes: 3
draft: false
unlisted: false
url: "https://www.derafu.dev/docs/data/container/introduction"
---

# Flexible Data Containers for PHP

[![GitHub](https://img.shields.io/badge/github-derafu%2Fcontainer-blue?logo=github)](https://github.com/derafu/container)
![GitHub last commit](https://img.shields.io/github/last-commit/derafu/container/main)
![CI Workflow](https://github.com/derafu/container/actions/workflows/ci.yml/badge.svg?branch=main&event=push)
![GitHub code size in bytes](https://img.shields.io/github/languages/code-size/derafu/container)
![GitHub Issues](https://img.shields.io/github/issues-raw/derafu/container)
![Total Downloads](https://poser.pugx.org/derafu/container/downloads)
![Monthly Downloads](https://poser.pugx.org/derafu/container/d/monthly)

A collection of specialized PHP data containers that provide different levels of structure and validation, from simple bags to schema-validated stores.

## Features

- 🎯 Purpose-built containers for different needs.
- 🔍 Validation with a simple schema (`Vault`) or with JSON Schema (`Store`).
- 🛡️ Validation on every change: a container never holds data that breaks its schema.
- 🔤 Typed getters (`getString()`, `requireInt()`, `getList(of: 'string')`...) that PHPStan understands.
- 📦 Simple to complex data structures, with dot notation.
- 🔄 Sequential data handling.
- 🧩 Common interface across containers.
- 🌐 Translatable exceptions.
- 🪶 Minimal dependencies.
- 🧪 Comprehensive test coverage.

## Why Derafu\Container?

Unlike generic data structures, Derafu\Container provides specialized containers each designed for specific use cases:

- **Bag**: Simple, flexible data storage without restrictions.
- **Vault**: Structured data validated with a simple schema (types, required keys, choices, defaults, normalizers).
- **Store**: Structured data validated with JSON Schema.
- **Journal**: Sequential data storage with LIFO access.

All of them share the same interface, so code that reads data does not care which container it received.

## Installation

Install via Composer:

```bash
composer require derafu/container
```

## A Quick Tour

```php
use Derafu\Container\Vault;

$options = new Vault(
    ['host' => 'imap.example.com'],
    [
        'host' => ['types' => 'string', 'required' => true],
        'port' => ['types' => 'int', 'default' => 993],
    ]
);

$host = $options->requireString('host'); // string: "imap.example.com"
$port = $options->requireInt('port');    // int: 993 (the default of the schema).

$options->set('port', 'abc');            // Throws: the port must be an int.
$options->getInt('port');                // Still 993: the failed change did nothing.
```

## Container Comparison

| Feature                   | Bag | Vault  | Store | Journal |
|---------------------------|-----|--------|-------|---------|
| Schema                    | No  | Simple | JSON  | No      |
| Validation on every change| No  | Yes    | Yes   | No      |
| Defaults and normalizers  | No  | Yes    | Defaults | No   |
| Nested data               | Yes | Yes    | Yes   | No      |
| Dot notation              | Yes | Yes    | Yes   | No      |
| Sequential                | No  | No     | No    | Yes     |
| Typed getters             | Yes | Yes    | Yes   | Yes     |

## Where to Go Next

- [Containers](containers): `Bag`, `Vault`, `Store` and `Journal` one by one.
- [Typed Getters](typed-getters): read values with the type you expect.
- [Validation](validation): schemas, when they are checked and what happens when they fail.
- [Translations](translations): the exceptions of the package and how to translate them.



---
Last updated on 20/10/2026

