PHPackages                             dulivu/irbis - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Framework](/categories/framework)
4. /
5. dulivu/irbis

ActiveLibrary[Framework](/categories/framework)

dulivu/irbis
============

Micro-Framework MVC

v2.6(9mo ago)247GPL-3.0-onlyPHP

Since Jan 18Pushed 3mo ago1 watchersCompare

[ Source](https://github.com/Dulivu/Irbis)[ Packagist](https://packagist.org/packages/dulivu/irbis)[ RSS](/packages/dulivu-irbis/feed)WikiDiscussions main Synced yesterday

READMEChangelog (8)DependenciesVersions (9)Used By (0)

Irbis Framework
===============

[](#irbis-framework)

PHP MVC Micro-Framework.

Enfocado en desarrollo modular.

Contenido
=========

[](#contenido)

1. [Introducción](#introduccion)
    - Parametrización
    - Modularidad
2. [Instalación](#instalacion)
3. [Configuración](#configuracion)
    - Seguridad
    - Gestión de aplicaciones
4. [Arquitectura](#arquitectura)
    - Controladores
    - Solicitud y Respuesta
    - Base de datos
5. [ORM](#orm)
    - Modelo
    - Recordset y Record
6. [Extensibilidad](#extensibilidad)
    - Interfaces
    - Hooks
    - Setup y Session

1. Introducción, características escenciales
============================================

[](#1-introducción-características-escenciales)

**Irbis** es un framework PHP ligero y modular que combina:

- Un **core MVC minimalista** (Request &gt; Controller &gt; Action &gt; Response)
- Un **sistema de módulos desacoplado**, permitiendo añadir logica por capas
- Un **ORM declarativo propio** con soporte nativo para **SQLite, MySQL y PostgreSQL**

El objetivo es ofrecer una base sólida, extensible y entendible para construir aplicaciones web y APIs.

`index.php` punto de entrada del sistema:

```
require 'vendor/autoload.php';

Irbis\Server::listen();
```

Esto es todo lo que requieres en tu punto de entrada, el framework está hecho para trabajar con urls amigables y `composer`, asegurate de configurar bien tu servidor web apache o ngix correctamente para esto.

`.htaccess`, de ejemplo para apache

```

  Order allow,deny
  Deny from all

Options +FollowSymLinks
RewriteEngine On

RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ index.php?$1 [QSA,L]
```

Tip

Esta configuración deniega el acceso a archivos `.ini` y `.db3` por seguridad.

Tip

También hace que toda solicitud de cliente este direccionada al archivo `index.php`.

1.1. Parametrización del sistema
--------------------------------

[](#11-parametrización-del-sistema)

El framework genera de forma automática un archivo `state.ini` para persistir su parametrización, este archivo se irá ajustando conforme vayas configurando tu sistema.

`state.ini`

```
[server]
debug = "on"
terminal = ""
[database]
dsn = "sqlite:database.db3"
user = ""
pass = ""
```

Para el ejemplo:

- El modo `debug` está activado, variable que recorre el sistema.
- La conexión de base de datos apuntan a `SQlite` por defecto.

Note

A nivel de código se puede manipular por medio de métodos `setState()` y `getState()` del objeto `Server`.

```
$server = Irbis\Server::getInstance();
// apuntando a una base de datos mysql
$server->setState('database.dsn', 'mysql:host=localhost;dbname=mydb;charset=utf8mb4');
$server->setState('database.user', 'db_username');
$server->setState('database.pass', 'db_password');
```

1.2. Modularidad
----------------

[](#12-modularidad)

El framework permite encapsular lógica de negocio en paquetes llamados módulos o aplicaciones, estos son directorios que contienen una estructura que el objeto `Server` leerá y gestionará.

Cada aplicación añadida, agregará lógica y/o funcionalidad al sistema.

Toda aplicación se estructura en un directorio principal, que es el paquete, y sus sub-directorios que son las aplicaciones. Pudiendo tener así un Paquete llamado `MyApps` y dentro varias aplicaciones como `Test`, `Rest`, etc.

`MyApps/Test` y `MyApps/Rest` ejemplo:

```
MyApps
  > Test
    > assets
      - script.js
      - style.css
    > components
    > models
      - users.php
      - groups.php
    > views
      - index.html
      - info.html
    - Controller.php
    - Hooks.php
    - Setup.php
  > Rest
    - Controller.php
- index.php

```

Important

Toda aplicación debe tener una clase `Controller.php` que es el controlador de la aplicación.

Tip

Adicionalmente puede implementar las clases `Hooks.php` y `Setup.php` para implementar ganchos de instalación y lógica de configuración como middlewares y otras funcionalidades.

Tip

Dentro del sistema una aplicación se identifica por su espacio de nombre `namespace` que sería la combinación de su paquete y su nombre, e: `MyApps/Test`

2. Instalación, el código fuente
================================

[](#2-instalación-el-código-fuente)

Important

- Se recomienda utilizar `composer` para instalar los fuentes, información **[aqui](https://getcomposer.org/download/)!**
- Se recomienda instalar `Git`, ya que algunas operaciones pueden requerirlo.

```
composer require dulivu/irbis

```

El comando de arriba instalará los fuentes del framework, luego sólo es necesario preparar el archivo `index.php` con el siguiente contenido y listo, estarás listo para iniciar.

`index.php`

```
require 'vendor/autoload.php';

Irbis\Server::listen();
```

Una vez instalado puedes ingresas a la **url, direccion IP, o localhost**, dependiendo del ambiente donde lo hayas instalado, podrás observar una pantalla en el navegador parecido a un terminal de comandos. Desde este terminal puedes continuar la configuración del sistema.

[![terminal capture](docs/terminal.png)](docs/terminal.png)

3. Configuración, usando el terminal
====================================

[](#3-configuración-usando-el-terminal)

El terminal es una interfaz de texto que permite interactuar directamente con la aplicación mediante la escritura de comandos en lugar de elementos gráficos.

Warning

Esta terminal sólo es una simulación, no tiene acceso real a comandos del equipo donde este instalado el sistema.

3.1. Seguridad
--------------

[](#31-seguridad)

Lo primero es asegurar el acceso al terminal.

- El comando `usermod` cambia el nombre de usuario del terminal
- El comando `passwd` cambia la contraseña de acceso.

Note

cambia `` y `` por el nombre de usuario y contraseña que desees usar.

```
$ usermod
$ passwd
```

Warning

Si sólo cambias la contraseña, el usuario por defecto es `irbis`

- El comando `clear` recarga un nuevo terminal limpio.

```
$ clear
```

Note

Luego de este ultimo paso, el navegador te solicitará ingreses el usuario y contraseña para poder continuar de ahora en adelante.

3.2. Gestión de aplicaciones
----------------------------

[](#32-gestión-de-aplicaciones)

Como vimos anteriormente, una aplicación tiene un espacio de nombre, compuesto por su directorio paquete y sub-directorio aplicación, resultando en un nombre similar a `MayApps/Test` ó `MyApps/Rest` esta nomenclatura identificará a cada aplicación dentro del sistema de forma única.

Tip

*Te comparto un repositorio con aplicaciones del mismo framework.*

Es un buen ejemplo para revisar como se estructura un paquete de aplicaciones y varias son muy útiles si deseas probarlas.

- El comando `git clone` replica un repositorio en tu sistema.

```
$ git clone https://github.com/dulivu/IrbisApps
```

- El comando `newapp` te permite crear una aplicación vacia.

```
$ newapp Test
```

Note

Se crea dentro del paquete `MyApps` por lo que su namespace sería `MyApps/Test`.

**No debe contener espacios ni carácteres especiales.**

- El comando `install` instala una aplicación disponible.

```
$ install MyApps/Test
```

- El comando `ls apps` muestra las aplicaciones disponibles.

```
$ ls apps
```

```
[ ] IrbisApps/Base
[ ] IrbisApps/Cms
[*] MyApps/Test

```

Note

Las aplicaciones ya instaladas se muestran con un **asterisco**.

Si la aplicación instalada tuviera alguna dependencia de otra, las dependencias se intentarán instalarán automáticamente.

- El comando `info` muestra información detallada de alguna aplicación.

```
$ info MyApps/Test
```

- El comando `remove` intentará quitar una aplicación del sistema, **pero ten cuidado** que esto no siempre puede ser beneficioso. *Si deseas probar aplicaciones se recomienda hacerlo en un ambiente de prueba.*

```
$ remove MyApps/Test
```

Tip

Si terminas instalando la aplicación creada y navegas a la raíz del sistema (ip, url o localhost) podrás observar que ya tienes respuesta :).

- El comando `nano` abré una ventana para editar un archivo. Si el archivo no exite lo crea.

```
$ nano Test/Controller.php
```

Note

Sólo puedes editar archivos que estén dentro del paquete `MyApps`.

- Algunos archivos se crean con una plantilla base.

```
$ nano Test/views/index.html
```

- Finalmente el comando `show` abre una ventana con la vista principal del sistema.

```
$ show
$ show /ruta/amigable
```

4. Arquitectura, lo básico e importante
=======================================

[](#4-arquitectura-lo-básico-e-importante)

A nivel técnico y de forma resumida dentro del patrón MVC implementado, existen 5 objetos que gestionan todo el flujo de una solicitud de cliente.

- **Server**: Orquestador principal del framework
- **Request**: Envoltura a los datos de la solicitud (GET, POST, HEADERS, COOKIES, etc.)
- **Controller**: El manejador principal de cada aplicación.
- **Action**: Envoltura de métodos auto-ejecutables por la solicitud del cliente.
- **Response**: Gestiona los datos y la forma de entregar una respuesta al cliente.

4.1. Controladores
------------------

[](#41-controladores)

Todo controlador debe heredar de la clase `Irbis\Controller` y debe declarar una propiedad `$name` que debe ser única en la lista de aplicaciones instaladas.

`MyApps/Test/Controller.php`

```
namespace MyApps\Test;
use Irbis\Controller as iController;

class Controller extends iController {
  public static $name = 'test';

  /**
   * @route /
   */
  final public function index () {
    return '@test/index.html';
  }
}
```

Cada método del controlador declarado con la palabra clave `final` representa una solicitud (`Action`) que el cliente puede invocar, además tambien debe tener una sección de comentarios correctamente estructurada ([DocBlock](https://docs.phpdoc.org/guide/getting-started/what-is-a-docblock.html)) y dentro un decorador `@route` que indica a que ruta responde dicha acción.

Important

`Server` revisará la solicitud `Request` y pedirá a cada `Controller` que entregue sus `Action` que coínciden con la solicitud, estos `Action` serán entregados a `Response` para que pueda determinar la respuesta.

### Métodos de utilidad

[](#métodos-de-utilidad)

```
// siendo $ctrl el objeto Controller
$ctrl->namespace();             // 'MyApps/Test'
$ctrl->namespace('php');        // '\MyApps\Test\'
$ctrl->namespace('snake');      // 'myapps_test_'
$ctrl->namespace('dir');        // '/var/www/MyApps/Test'
```

```
// ejecuta la última acción de la pila
$ctrl->super();
// obtiene la instancia de un controlador del sistema
$ctrl->application('MyApps/Test')
// fabrica y devuelve un objeto componente
$ctrl->component('Model');
```

4.2. Solicitud y Respuesta
--------------------------

[](#42-solicitud-y-respuesta)

El objeto `Request` es un singleton, por lo que sólo puede existir una sola instancia en cada ejecución, si necesitas utilizarlo puedes llamarlo por su método `getInstance()`.

```
$request = Irbis\Request::getInstance();
```

### Métodos de utilidad

[](#métodos-de-utilidad-1)

```
$request->isGet();
$request->isPost();
$request->isPut();
$request->isPatch();
$request->isDelete();
$request->isJson(); // si la solicitud lleva cabecera 'application/json'
$request->cookie($key) // devuelve un valor en las cookies
```

```
$request->cookie($key) // devuelve un valor de las cookies enviadas
$request->header($key) // devuelve un valor de las cabeceras de solicitud
```

- Leyendo datos de cliente

```
$request->query($key) // devuelve un valor de la url (GET)
$request->input($key) // devuelve un valor del body (POST)

// otro ejemplos
// URL: /search?q=irbis&page=2&filter=
$request->query('q');           // 'irbis'
$request->query('*');           // ['q' => 'irbis', 'page' => '2', 'filter' => '']
$request->query('*!');          // ['q' => 'irbis', 'page' => '2']
$request->query(['q', 'page']); // ['q' => 'irbis', 'page' => '2']
```

```
// normalmente datos enviados por formularios POST
$request->input('username');    // el valor del input[@name='username']
$request->input('*');           // todos los valores enviados por POST
```

```
// @route /users/(:num)
// URL: /users/5
$request->path(0);              // 5

// @route /blog/(:any)/section/(:num)
// URL: /blog/entrada-1/section/7
$request->path(0);              // 'entrada-1'
$request->path(1);              // 7
```

- Leyendo archivos cargados por el cliente

```
$request->hasUploads(); // true si hay archivos, ó false
$request->hasUploads($key); // validar si se subieron archivon con clave '$key'

// guardar un archivo subido por el cliente
// $key, es la clave con la que se sube el archivo
$request->upload($key, '/path/to/file');
```

- Un ejemplo de un método en un controlador para subir multiples archivos. *Debes crear un directorio `uploads` dentro de tu aplicación.*

```
/**
 * @route /upload
 */
final function uploadFiles ($request, $response) {
  $key = 'file'; // clave del archivo subido

  if ($request->isPost() && $request->hasUploads()) {
    $request->walkUploads($key, fn($upload) => {
      $basepath = $this->namespace('dir') . 'uploads/';
      $filepath = $basepath.$upload['name'];
      move_uploaded_file($upload['tmp_name'], $filepath);
    });
  }

  return '@test/upload.html';
}
```

Note

En el último ejemplo se observa que a cada `Action` se le pasa tambien dos parámetros `Request` y `Response` que puedes utilizar dentro de la lógica de la acción para tomar decisiones y determinar la información entregada al cliente.

---

El objeto `Response` es pasado al método del controlador `Action` como un segundo parámetro (opcionalmente utilizable).

### Métodos de utilidad

[](#métodos-de-utilidad-2)

```
$response->view($view); // establece una vista para mostrar
$response->hasView(); // true si tiene una vista establecida
```

```
$response->header($key, $value); // establece una cabecera de respuesta
$response->body($data); // establece los datos para pasar a la vista

$response->append($key, $value); // agrega un valor al cuerpo de respuesta
$response->remove($key); // quita un valor al cuerpo de respuesta
```

- Para simplificar la gestión de la respuesta existe algunas interpretaciones que `Response` reconoce en función de lo que la acción del controlador devuelva.

> Si se devuelve un texto plano u otro tipo de dato, `Response` lo interpreta como `body`

```
/**
 * @route /
 */
final public function index () {
  return 'Mi nueva aplicación';
}
```

> Si se devuelve una ruta a una vista html, `Response` lo interpreta como `view`
>
> Además el acortador `@test` es reemplazado por la ruta `MyApps/Test/views` de la aplicación, para buscar la plantilla exactamente en ese directorio.

```
/**
 * @route /
 */
final public function index () {
  return '@test/index.html';
}
```

> Si se devuelve una combinación \[`view`,`data`\], `Response` establece precisamente esa información usando internamente `view()` y `body()` y dentro de la plantilla `index.html` esos datos estarán disponibles.

```
/**
 * @route /
 */
final public function index () {
  return ['@test/index.html', ['msg' => 'Hola mundo!']];
}
```

> Lo anterior es lo mismo que aplicar dichos métodos de forma explicita, y usando el objeto `Response` además podemos controlar otros aspectos como las cabeceras de respuesta.

```
/**
 * @route /
 */
final public function index ($request, $response) {
  $response->header('Content-Type: text/html');
  $response->view('@testweb/index.html');
  $response->data(['msg' => 'Hola mundo!']);
}
```

Note

Hasta este punto ya puedes levantar un sitio web con información dinámica, controlar el flujo desde la solicitud hasta la entrega de información al cliente, tener ordenadas tus rutas con URLs amigables y las plantillas `html` que necesites.

Tip

**Reto:** Crea un archivo `css` y agregalo en `index.html` para aplicar estilos a tu sitio web. Una Pista, para agregar un activo utiliza la ruta completa del módulo e: ``.

> Comandos:

```
$ nano Test/assets/style.css
$ nano Test/views/index.html
```

4.3. Base de datos
------------------

[](#43-base-de-datos)

Ahora vamos adentrandonos en temás cada vez más complejos, el framework maneja de forma automatica una conexión a base de datos, vimos en la [primera parte](#introduccion) que existe un archivo de parametrización `state.ini` que por defecto apunta a `SQLite` ahí puedes modificar si deseas utilizar `MySQL` o `PostgreSQL`.

- El commando `conn` permite configurar los parámetros de conexión a base de datos.

```
$ conn reset
$ conn dsn
$ conn user
$ conn pass
```

- `reset` le indica al sistema que debe reinicializar sus parámetros de conexión, usando por defecto `SQLite`.

---

Así que prácticamente con el mínimo (o nada) de configuración puedes usar el objeto `Irbis\Orm\Connector` para empezar a ejecutar sentencias `SQL`.

- El comando `sql` abre una ventana para ejecutar sentencias SQL. **Sólo funciona con conexiones a SQLite**.

```
$ sql
```

Note

Para el siguiente ejemplo puedes crear una tabla `todo_list` en tu base de datos.

```
CREATE TABLE IF NOT EXISTS "todo_list" (
  "name" VARCHAR NOT NULL,
  "is_done" BOOLEAN
);
```

> Inserta un par de datos a la tabla.

```
INSERT INTO "todo_list" ("name") VALUES
  ('aprender a usar Irbis'),
  ('crear mi propio sistema');
```

> Revisa los datos insertados.

```
SELECT * FROM "todo_list";
```

---

Ahora que los datos están listos, vamos a implementar en nuestra aplicación `MyApps/Test` una vista que muestre esa información.

> Primero crearemos la vista `html`

```
$ nano Test/views/index.html
```

> Agrega este codigo dentro del `body`

```
Lista de cosas por hacer

```

> Ahora modificaremos el controlador.

```
$ nano Test/Controller.php
```

```
