Comparar tamaños
English Français

PHP Data Access Libraries (ORM, ActiveRecord, Persistence)

For description on the comparison criteria, please read full article here:
DoctrineAgile DataEloquentYii ORMCake ORMFuel ORMRed Bean PHPTingSpiral ORM..
DescripciónData Access Framework for high-latency databases (Cloud SQL/NoSQL).RedBeanPHP is an easy to use ORM for PHP. It's a Zero Config ORM lib that 'automagically' builds your database schema.Simple: no magic inside : it’s basically SQL queriesORM engine with automatic database scaffolding, strict schemas, code discovery, modular database partitions and various relation loaders.
Github / Bitbucket /
LicenseMITMITBSD-3New BSD / GPLApache 2MIT
Latest version2.5.51.2.x2.
How schema is defined?PHP, XML, YAMLin PHP. Method init() in Model class defines fields, relations, conditions, etc.Model class propertiesActive record magic properties.Automatically discovered on the fly.PHPPHP Const array. Column class.
Code generation schema-tool Web and console generator
Can be used in Any Framework composer / packagist Through composer/packagist Through Capsule- Planned in 2.1.x composer / packagist
Automated Cache Frameworks focuses on optimizing queries rather then caching. Still possible with cross-persistence saving.
Anti-patterns (purposely included)Model close-coupled with Persistence and Field classes.Eloquent is a God Class; Global functions; DB Conection is global;
DependenciesMedium: ±5 packages.Minimal: 2 packages: DSQL Query Builder ( 3, pimple, doctrine/cache, aura/sqlquery
sin puntuaciones
5.0/5 2 Calificaciones
sin puntuaciones
5.0/5 2 Calificaciones
5.0/5 1 Valoración
sin puntuaciones
sin puntuaciones
5.0/5 1 Valoración
sin puntuaciones
sin puntuaciones
Enterprise Compliance
5.0/5 1 Valoración
5.0/5 2 Calificaciones
3.0/5 1 Valoración
4.5/5 2 Calificaciones
5.0/5 1 Valoración
sin puntuaciones
sin puntuaciones
5.0/5 1 Valoración
sin puntuaciones
sin puntuaciones
Minimum PHP Version5.
Basic Features
PDO Support Yes Yes- But made a custom driver to support it is easy
Transparent support for NoSQL- Through 3rd party drivers.No Eloquent is built on Query Builder. Perhaps moloquent? Also - Through Caching backend, but not as ORM native persistence. Avialable cross sql and nosql datababase relations ( Build around plain queries.NoNo No, through ODM (
How to invoke db-vendor-specific extensions? DBAL For SQL - save/load/delete operations are expressed in DSQL Queries that can be manipulated: Through Query Builder / RAW queries. SQL - Query Builder.- Can add SQL code chunks. Ting use native query, you can use everyting of your SGBD Query models:
Array as a persistence CRUD operations supported
RestAPI as a persistence- Through 3rd party extension.- To extend BaseActiveRecordNoNo
JSON string as a persistence Supported with few extra lines of code.- To extend BaseActiveRecordNoNo
Same model, multiple persistences Same class. Different object.- (no docs)
Basic Single-record operations (C,R,U,D)
Table Name Mapping Yes Yes Same as model class name by default Using static method of active record. mapping no longer supported. Yes
Field Name Mapping Yes, (Annotations in PHP) Yes (Field::actual property)- Through accessors/3rd party extensionNo mapping no longer supported. Yes
Map Entity to SubQueryNo Must be physical table Yes. Extension exist for UNION-models. Must be physical table.- table = new Expression(..)NoNo This concept is no-sense for Ting
Map property to expressionNo Must be physical field $model->addExpression()No Must be physical table- (couldn't find docs)NoNo This concept is no-sense for Ting
Map native types (DateTime) $field->type = 'date' Accessors and Mutators Active record behaviors Yes- No support for DateTime.
User-defined types (e.g. "23 USD") Type class Yes. Independent from Model. by extending Field class. Accessors and Mutators Active record behaviors Yes, with custom serializer
Map field of related Entity ('currency' = currency_id->Model Specific record only Transparently maps into sub-select.- Relationship, but only single record. $model->currency->nameNo Yes
Map field to sub-query on related entity (Client.balance = Client->orders->sum(total))No Yes. hasMany()->addField(..aggregate)No- (couldn't find docs)No- This concept is no-sense for Ting
Entity to join multiple tables (adding new record populates both tables) Associations $model->join('other_table')NoNo No native support.No Yes
Criteria, Scope, Conditions (Model will refuse to work with records that does not match criteria)
Support model-level criteria Yes. Applied on loading / saving / update.- Global Scope (querying only)NoNo
Soft-delete Extension Through criteria. Example given in the docs. Trait and Scope Events and behaviorsNo
Domain Model Criteria $m->addCondition('gender','M'); where 'gender' can be arbitrary expression, sub-select, field from association(join) or mapped no another physical field.- Scopes, but not in domain model.No Only for specific query: User::find()->byEmail('...')->active()->one()No
Expression-based condition $m->addCondition($m->expr('..')); through Query BuilderNo Only for query: User::find()->andWhere('...')->all()No
Criteria Compliance (new record must match condition) Transaction rollback and exception. Automated-rloading.NoNo
Dynamic criteria $user->addCondition('is_expired', false)No Only Querying: User::find()->where(['a' => '1', 'b' => true])->all();No
Query Building (Convert Model into Query object for further SQL tweaking)
Convert Model into Query Object $q = $model->action('select'); Model is a Query object. See: Model::where() \yii\db\ActiveRecord::find()No RecordSelector
Raw expression new Expression('any sql') DB::raw() new \yii\db\Expression('...')
Nested/Composite Queries/Expressions Expression can be in any part of queryNo Expression can be in any part of queryNo
Reference domain-model field in query through Expressionable interfaceNo No fields. Only properties.No Field is class property.NoNo
field, where, order, limit Expressions and Parametric values \yii\db\ActiveQueryNo
options, rollup, partition- Through custom templates, or expressions.- not sure.
UPDATE, DELETE, INSERT query buildingNo
REPLACE, TRUNCATE- Throught raw sql in \yii\db\Command- wipe(),
SHOW, DESCRIBE, CALL- Supported through Expressions or Custom query template- Throught raw sql in \yii\db\Command- Automatic schema alter / discovery.
ALTER, CREATE query building Addon:
User-defined query template Templates for all queries (please link doc)No
full support for OR conditions Through Object Composition and Expressions- Partial-No only raw query
Use Domain logic in multi-record update- Supported, but must map fields/values manually.NoNoNo
Data Fetching (different ways to retrieve data from database)
Get All Data (2x array) \yii\db\Query::all() exportAll()
Associative Array (id=>value)No Planned lists()
Select only required fields
Typecasting (e.g. DateTime)
Import (multiple records)
Respect domain model mapping (and criteria)
Single row loadAny \yii\db\Query::one()
Single Value Through action \yii\db\Query::scalar()
Single Column- may need to map resulting array \yii\db\Query::column()
Bypass persistence mapping action('select')->getAll() ?? (e..g prevent date from being transformed into Carbon)
Loading and Saving individual records
Load by ID load(id) User::findOne(1) get(id) findByPK
Load by other field loadBy('field', $value) User::findOne(['id' => 1])No getBy(['propertyName' => 'value']);
Read-only Models YesNo
Model without primary key Yes, but only in Read-only ModeNo
Specify fields to load onlyFields()No Fields load with SELECT * User::find()->select([])->one()No
Save only sends dirty fields- (there is Dirty support, so I assuming it is supported)
Guarded / Fillable properties Conditions and OnlyFields do same thing but more reliably. Prevents "create($_GET)" from messing up important fields.
Object Hierarchy Model
Admin extends User, adds criteria (is_admin=1) Yes, recommended pattern. "User" class adds condition.NoNo Can be done as wrapper: User::findAdmin(..) or custom CDbCriteriaNo
Admin extends User, adds accessible fields Yes, recommended pattern.NoNoNo
Extend model, add Join (Disjoined SubTypes) Yes. Unlimited number of joins.NoNoNo
Extend model change table Yes. Used to tweak 3rd party models.No
Relations/References (One model can relate to another model. NOT A TABLE JOIN)
Model can define relation to other Model References are implemented as Objects Relations Relations
One-to-Many $user->hasMany('Orders', new Order());
One-to-many traversal strategyReturns destination model instance with dynamically applied criteria (parent_id=123). No queries are executed. Inserting record into this model will ensure association with parent model.Returns array of objects that may either be pre-loaded with record data or only contain IDs (lazy-loaded).Uses classical eager/lazy loading approach. with() can help pre-fetch the data for related entities.pre-fetch and store objects in an array.
Lazy/Eager-loadingNo Anti-pattern
One-to-One $order->hasOne('user_id', new User());
Many-to-Many $user->addCondition('vip', true)->ref('Orders'); relations() method of an entity can define.
Deep Many-to-Many traversal.No $user->ref('Orders')->ref('Payments')->action('count'); No intermediate queries.- only with "to-one" references: $book->author->address->street; Executes multiple queries.- only with to-one references. Executes multiple queries.
Cross-Persistence traversal $user->hasMany('Log', new Log($mongodb));- No docs.No
Cross-persistence joins, aggregation, reporting
Multi-persistence joinNoNoNoNo
UNION existing modelsNo Yes, in add-on Can join UNION result with more tables.NoNo
Domain-model Aggregation Group by multiple fields. Apply aggregation functions. Preserve types.No
Model to Model joinNo Planned.No
Multi-persistence UNIONNoNoNoNo
Behaviours / Hooks
Before/After operation
Override standard C,R,U,D operations
Persistence-specific hooks (to modify Query)- (no docs)
User-defined hooks
Global Auditing
Store old/new field values Yes in JSON and user-readable string.
Revert action (undo) and replay (redo)NoNo
Reactive actions Each action will be automatically linked with sub-actions which may be invoked through Hooks.
Store log in any persistenceNo
Override, Add fields to audit logRecord dirty fields before persisting. Type-cast into JSON string and store in a single field of AuditLog Model. This model can be persisted anywhere, table, file, etc.
Custom events
Access to record-specific history $item->ref('AuditLog');- Through a custom query.
Date of creation, modification- No but easy to add through hook. \yii\behaviors\TimestampBehavior TimestampTrait
User/IP creation, modification- Easy to add through a hook. \yii\behaviors\BlameableBehavior
Store incremental revisions- Easy to add through a hook
Field meta-information providedType, caption, possible values, mapped field, join table spec, encryption, serialization, UI-specific settings, validation rules.
UI extensionsNo CRUD, Form, Table, Grid, Entity-manager. (see
API extensions RestFULL API, automated CRUD operations + RPC
Me gusta
Compare Doctrine vs Agile Data vs Eloquent vs Yii ORM vs Cake ORM vs Fuel ORM vs x vs x
2017-12-21 16:47:00
View changes
Manage backups

User reviews and comments