granadaorm / granada
支持预加载、延迟加载的 Active Record / ORM
Requires
- php: >=8.1
Requires (Dev)
- phpstan/phpstan: ^1.11
- phpunit/phpunit: ^9.0
Suggests
- granadaorm/builder: Automatically build model classes from the database schema
- granadaorm/form: Quick generate html forms from the model structure using css frameworks such as Bootstrap and Bulma
Replaces
- surt/granada: *
This package is auto-updated.
Last update: 2024-09-09 06:29:53 UTC
README
Granada 是一个易于使用的 Active Record 实现,基于 Idiorm/Paris 的 ORM。
快速浏览
use Granada\Model; class User extends Model { public function posts() { return $this->has_many('Post'); } } class Post extends Model {} // select $user = User::where('name', 'John')->find_one(); // modify $user->first_name = 'Doe'; $user->save(); // select relationship $posts = $user->posts()->find_many(); foreach ($posts as $post) { echo $post->content; }
您可以在 paris.readthedocs.org 阅读Paris文档,但请务必阅读以下补充内容。
安装
使用 composer
composer require granadaorm/granada
配置
require 'vendor/autoload.php'; use Granada\ORM; ORM::configure('mysql:host=localhost;dbname=my_database'); ORM::configure('username', 'database_user'); ORM::configure('password', 'top_secret');
如常,您可以在 Paris 文档 中详细了解。
补充
预加载
您可以使用 "with" 方法将关系预加载添加到查询中。
$results = User::with('avatar', 'posts')->find_many();
将使用3个查询来获取用户及其关系
SELECT * FROM user SELECT * FROM avatar WHERE user_id IN (....) SELECT * FROM posts WHERE user_id IN (....)
您可以按这种方式为每个结果获取关系的查询结果
foreach($results as $result){ echo $result->avatar->img; foreach($result->posts as $post){ echo $post->title; } }
延迟加载
尝试访问尚未获取的关系将调用并返回它
$results = User::find_many(); foreach($results as $result){ echo $result->avatar->img; }
注意,如果在上面的示例中没有 "avatar" 的结果,它将抛出 Notice: Trying to get property of non-object...
注意:可能值得为此用例和其他用例创建一个 NULL 对象。
带有预加载参数的链式关系
您可以链式调用关系并为关系调用添加参数
// chained relationships with dot notation $results = User::with('posts.comments')->find_many(); // OR // chained relationships use the "with" reserved word. (usefull if you want to pass arguments to the relationships) $results = User::with(array('posts'=>array('with'=>array('comments'))))->find_many(); // SELECT * FROM user // SELECT * FROM post WHERE user_id IN (....) // SELECT * FROM comments WHERE post_id IN (....) foreach($results as $result){ foreach($posts as $post){ echo $post->title; foreach($post->comments as $comment){ echo $comment->subject; } } } // you can use arguments (one or more) to call the models relationships $results = User::with(array('posts'=>array('arg1')))->find_many(); // will call the relationship defined in the user model with the argument "arg1"
自定义查询过滤器
可以在模型上创建静态函数作为查询中的过滤器。以 "filter_" 开头
use Granada\Model; class ModelName extends Model { .... public static function filter_aname($query, $argument1, $argument2...){ return $query->where('property', 'value')->limit('X')......; } .... }
并在静态调用中使用它
ModelName::aname($argument1, $argument2)->....
Granada 的多个补充名称
- select_raw
- group_by_raw
- order_by_raw
- raw_join
- insert : 从数组创建并保存多个元素
- pluck : 从结果返回单个列。
- find_pairs : 返回键=>值的数组作为结果
- save : 接受一个布尔值以使用 "ON DUPLICATE KEY UPDATE"(仅适用于 Mysql)
- delete_many (接受连接子句)
重载 SET
// In the Model protected function set_title($value) { $this->alias = Str::slug($value); return $value; }
// outside of the model $content_instance->set('title', 'A title'); // works with multiple set too $properties = array( 'title' => 'A title', 'content' => 'Some content' ); $content_instance->set($properties); // try it with a direct assignement $content_instance->title = 'A title';
重载 GET 和缺失属性
// In the Model // Work on defined protected function get_path($value) { return strtolower($value); } // and non-defined attributes. protected function mising_testing() { return 'whatever'; } ... // outside of the model echo $content_instance->path; // returns the lowercase path value of $content_instance echo $content_instance->testing; // returns 'whatever' since we defined a missing_{attribute_name}
当然,您仍然可以定义具有属性名称的函数以完全重载它。
在模型上定义 resultSet(集合类型)类
现在可以定义模型实例结果返回的 resultSet 类。 (如果 return_result_sets
配置变量设置为 true)请注意,定义的 resultSet 类必须 extends Granada\ResultSet
并必须加载
// In the Model public static $resultSetClass = 'TreeResultSet';
// outside of the model var_dump(Content::find_many()); // echoes object(TreeResultSet)[10] protected '_results' => array(...) ....
ResultSet 由模型在结果中定义,如您在上面所见。在预加载时,结果是一致的。例如,如果我们有一个 Content
模型,具有 $resultSetClass = 'TreeResultSet'
和一个 has_many
关系定义为 media
Content::with('media')->find_many();
将返回一个包含 Content
实例的 TreeResultSet
,每个实例都有一个包含 Granada\ResultSet
的 property $media
(如果没有在模型上定义,则为默认的 resultSet)
基本文档来自 Paris
Paris
功能完整
自 1.4.0 版本起,Paris 被认为功能完整。虽然它将继续通过错误修复进行维护,但不会添加更多新功能。
PHP5 的轻量级 Active Record 实现。
建立在 Idiorm 之上。
在 PHP 5.2.0+ 上进行了测试 - 可能可以使用 PDO 和正确的数据库驱动程序在更早的版本上运行。
在 BSD 许可证 下发布。
功能
- 极其简单的配置。
- 公开了Idiorm流畅查询API的全部功能。Idiorm。
- 支持关联。
- 简单的机制来封装常用的查询在过滤器方法中。
- 基于PDO构建。
- 始终使用预处理语句,以防止SQL注入攻击。
- 数据库无关性。目前支持SQLite、MySQL、Firebird和PostgreSQL。可能支持其他数据库,请尝试一下!
- 支持通过方法链对模型集合进行过滤或一次性对多个结果应用操作。
- 支持多个连接。
历史
Granada最初由Erik Wiesenthal开发,版本为1.5。进一步的开发由Josh Marshall开始,以发布版本2.0。