关联关系

一对一

users表和上面的posts表为一对一关联关系,通过posts.author_id字段关联,userspost表结构如下:

  1. CREATE TABLE `posts` (
  2. `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  3. `author_id` int(10) unsigned NOT NULL ,
  4. `title` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
  5. `content` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
  6. `rate` int(255) COLLATE utf8_unicode_ci NOT NULL,
  7. `release_at` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
  8. `created_at` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
  9. `updated_at` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
  10. PRIMARY KEY (`id`)
  11. ) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;
  12. CREATE TABLE `users` (
  13. `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  14. `name` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
  15. `email` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
  16. `created_at` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
  17. `updated_at` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
  18. PRIMARY KEY (`id`)
  19. ) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;

模型定义为:

  1. class User extends Model
  2. {
  3. }
  4. class Post extends Model
  5. {
  6. public function author()
  7. {
  8. return $this->belongsTo(User::class, 'author_id');
  9. }
  10. }

数据仓库定义为:

  1. <?php
  2. namespace App\Admin\Repositories;
  3. use Dcat\Admin\Repositories\EloquentRepository;
  4. use User as UserModel;
  5. class User extends EloquentRepository
  6. {
  7. protected $eloquentClass = UserModel::class;
  8. }

那么可以用下面的方式显示post所属的用户的详细:

  1. use App\Models\User;
  2. $show->author(function ($model) {
  3. return Show::make($model->author_id, new User(), function (Show $show) {
  4. $show->resource('/users');
  5. $show->id();
  6. $show->name();
  7. $show->email();
  8. });
  9. });

{tip} 为了能够正常使用这个面板右上角的工具,必须用resource方法设置用户资源的url访问路径。

如果你的关联模型还需要有其他的条件查询,则可以参考以下方式

  1. use App\Models\User;
  2. $show->author(function ($model) {
  3. // 模型设置查询条件
  4. $userModel = User::where('state', $model->state);
  5. return Show::make($model->author_id, $userModel, function (Show $show) {
  6. // 设置路由
  7. $show->resource('/users');
  8. $show->id();
  9. $show->name();
  10. $show->email();
  11. });
  12. });

简单方式

如果你只是简单的展示关联表信息,也可以这么写

  1. // 如果你用的是模型,可以这样指定关联关系
  2. $model = Post::with('author');
  3. // 如果你用的是数据仓库,可以这样指定关联关系
  4. // $repository = new Post(['author']);
  5. return Show::make($id, $model, function (Show $show) {
  6. $show->field('author.id', '作者ID');
  7. $show->field('author.name', '作者名称');
  8. ...
  9. });

如果你的关联模型名称的命名是驼峰风格,那么使用的时候需要转化为下划线风格命名

  1. // 注意这里必须使用下划线风格命名,否则将无法显示编辑数据
  2. $show->field('user_profile.postcode');
  3. $show->field('user_profile.address');

一对多

一对多会以数据表格的方式呈现,下面是简单的例子

posts表和评论表comments为一对多关系(一条post有多条comments),通过comments.post_id字段关联

  1. CREATE TABLE `comments` (
  2. `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  3. `post_id` int(10) unsigned NOT NULL,
  4. `content` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
  5. `created_at` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
  6. `updated_at` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
  7. PRIMARY KEY (`id`)
  8. ) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci

模型定义为:

  1. class Post extends Model
  2. {
  3. public function comments()
  4. {
  5. return $this->hasMany(Comment::class);
  6. }
  7. }
  8. class Comment extends Model
  9. {
  10. }

数据仓库定义为:

  1. <?php
  2. namespace App\Admin\Repositories;
  3. use Dcat\Admin\Repositories\EloquentRepository;
  4. use Comment as CommentModel;
  5. class Comment extends EloquentRepository
  6. {
  7. protected $eloquentClass = CommentModel::class;
  8. }

那么评论的显示通过下面的代码实现:

  1. use App\Admin\Repositories\Comment;
  2. $show->comments(function ($model) {
  3. $grid = new Grid(new Comment);
  4. $grid->model()->where('post_id', $model->id);
  5. // 设置路由
  6. $grid->resource('comments');
  7. $grid->id();
  8. $grid->content()->limit(10);
  9. $grid->created_at();
  10. $grid->updated_at();
  11. $grid->filter(function ($filter) {
  12. $filter->like('content')->width('300px');
  13. });
  14. return $grid;
  15. });

注意:为了能够正常使用这个数据表格的功能,必须用resource()方法设置comments资源的url访问路径

多对多

多对多会以数据表格的方式呈现,下面是简单的例子

角色表roles和权限表permissions为多对多关系,通过中间表role_permissions关联

  1. CREATE TABLE `roles` (
  2. `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  3. `name` varchar(50) COLLATE utf8mb4_unicode_ci NOT NULL,
  4. `slug` varchar(50) COLLATE utf8mb4_unicode_ci NOT NULL,
  5. `created_at` timestamp NULL DEFAULT NULL,
  6. `updated_at` timestamp NULL DEFAULT NULL,
  7. PRIMARY KEY (`id`),
  8. UNIQUE KEY `admin_roles_name_unique` (`name`)
  9. ) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;
  10. CREATE TABLE `permissions` (
  11. `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  12. `name` varchar(50) COLLATE utf8mb4_unicode_ci NOT NULL,
  13. `slug` varchar(50) COLLATE utf8mb4_unicode_ci NOT NULL,
  14. `http_method` varchar(255) COLLATE utf8mb4_unicode_ci DEFAULT NULL,
  15. `http_path` text COLLATE utf8mb4_unicode_ci,
  16. `order` int(11) NOT NULL DEFAULT '0',
  17. `parent_id` int(11) NOT NULL DEFAULT '0',
  18. `created_at` timestamp NULL DEFAULT NULL,
  19. `updated_at` timestamp NULL DEFAULT NULL,
  20. PRIMARY KEY (`id`),
  21. UNIQUE KEY `admin_permissions_name_unique` (`name`)
  22. ) ENGINE=InnoDB AUTO_INCREMENT=9 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;
  23. CREATE TABLE `role_permissions` (
  24. `role_id` int(11) NOT NULL,
  25. `permission_id` int(11) NOT NULL,
  26. `created_at` timestamp NULL DEFAULT NULL,
  27. `updated_at` timestamp NULL DEFAULT NULL,
  28. KEY `admin_role_permissions_role_id_permission_id_index` (`role_id`,`permission_id`)
  29. ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;

模型定义为:

  1. class Role extends Model
  2. {
  3. public function permissions() : BelongsToMany
  4. {
  5. return $this->belongsToMany(Permission::class, 'role_permissions', 'role_id', 'permission_id');
  6. }
  7. }
  8. class Permission extends Model
  9. {
  10. }

数据仓库定义为:

  1. <?php
  2. namespace App\Admin\Repositories;
  3. use Dcat\Admin\Repositories\EloquentRepository;
  4. use Permission as PermissionModel;
  5. class Permission extends EloquentRepository
  6. {
  7. protected $eloquentClass = PermissionModel::class;
  8. }

那么权限的显示通过下面的代码实现:

  1. use App\Admin\Repositories\Permission;
  2. $show->permissions(function ($model) {
  3. $grid = new Grid(new Permission);
  4. $grid->model()->join('role_permissions', function ($join) use ($model) {
  5. $join->on('role_permissions.permission_id', 'id')
  6. ->where('role_id', '=', $model->id);
  7. });
  8. // 设置路由
  9. $grid->resource('auth/permissions');
  10. $grid->id;
  11. $grid->name;
  12. $grid->slug;
  13. $grid->http_path;
  14. $grid->filter(function (Grid\Filter $filter) {
  15. $filter->equal('id')->width('300px');
  16. });
  17. return $grid;
  18. });