dozen-software/listcraft

从 Eloquent 模型创建列表。https://github.com/Dozen-Software/listcraft

1.0.2 2024-01-12 17:46 UTC

This package is not auto-updated.

Last update: 2024-09-20 23:13:47 UTC


README

Listify 的更新版本(lookitsatravis/listify)。

将任何 Eloquent 模型转换为列表!

描述

Listcraft 提供了对列表中多个对象进行排序和重新排序的功能。具有此指定功能的类需要在映射的数据库表上定义一个 position 列作为整数。

要求

  • Listcraft 当前需要 php >= 8.0(《Listcraft》通过 trait 实现)。
  • Laravel 9.0 或更高版本

安装

Listcraft 以 composer 包的形式分发,这是在您的应用程序中使用它的方式。

使用 Composer 安装该包。编辑您的项目 composer.json 文件,以要求 dozen-software/listcraft

  "require": {
    "laravel/framework": "~5.0",
    "dozen-software/listcraft": "~1.2"
  }

完成此操作后,最后一步是添加服务提供者。打开 app/config/app.php,向 providers 数组中添加一个新项目。

    'Dozensoftware\Listcraft\ListcraftServiceProvider'

可选地,您可以定义 Listcraft trait 的别名。打开 app/config/app.php,向 aliases 数组中添加一个新项目。

    'Listcraft' => 'Dozensoftware\Listcraft\Listcraft'

快速开始

首先,您需要添加一个用于存储位置的列。从命令行使用迁移生成器

php artisan listcraft:attach {table_name} {position_column_name}
php artisan migrate

{table_name} 是必需的参数。{position_column_name} 是可选的,默认值为 "position"。

然后在您的模型中

class User extends Eloquent
{
    use \Dozensoftware\Listcraft\Listcraft;

    public function __construct(array $attributes = array(), $exists = false) {

        parent::__construct($attributes, $exists);

        $this->initListcraft();
    }
}

确保在您的模型中调用 initListcraft() 方法后调用 parent::__construct()

这就是所有您需要做的,以便获得对 Listcraft 的访问。

概述

添加到 Eloquent 模型的实例方法

您将为每个添加了 Listcraft 的 Eloquent 模型实例添加一些方法。

Listcraft 中,“更高”表示列表的上方(更低的 position),而“更低”表示列表的下方(更高的 position)。这可能有点令人困惑,因此添加测试以验证您是否根据您的上下文使用了正确的方 法可能是有意义的。

更改位置和重新排序列表的方法

  • eloquentModel.insertAt(2)
  • eloquentModel.moveLower() 如果项目是最低的项目则不会执行任何操作
  • eloquentModel.moveHigher() 如果项目是最高项目则不会执行任何操作
  • eloquentModel.moveToBottom()
  • eloquentModel.moveToTop()
  • eloquentModel.removeFromList()

更改位置而不立即重新排序列表的方法

注意:更改后的位置仍会在模型保存时触发对列表中其他项目的更新
  • eloquentModel.incrementPosition()
  • eloquentModel.decrementPosition()
  • eloquentModel.setListPosition(3)

返回项目列表位置属性的方法

  • eloquentModel.isFirst()
  • eloquentModel.isLast()
  • eloquentModel.isInList()
  • eloquentModel.isNotInList()
  • eloquentModel.isDefaultPosition()
  • eloquentModel.higherItem()
  • eloquentModel.higherItems() 将返回列表中 eloquentModel 上方的所有项目(按位置排序,升序)
  • eloquentModel.lowerItem()
  • eloquentModel.lowerItems() 将返回列表中 eloquentModel 下方的所有项目(按位置排序,升序)

##配置

有几个配置选项可用。您需要将这些作为数组参数传递给模型构造函数中的 initListcraft()。以下是选项

  • top_of_list 设置列表顶部的整数位置(默认:1)。
  • column 设置你在安装过程中选择的位置列的名称(默认:'position')。
  • add_new_at 设置你在安装过程中选择的位置列的名称(默认:'bottom',选项:'top''bottom')。
  • scope 允许你限制列表中的项目。这一点需要稍作解释。它接受三个可能的值:
    • 字符串
    • Illuminate\Database\Eloquent\Relations\BelongsTo 对象
    • Illuminate\Database\Query\Builder 对象

###字符串

如果传递了 string,则将原始字符串作为 whereRaw 传递给作用域。这允许你执行类似 'custom_foreign_key = 42' 的操作,并将所有项目限制在结果集中。你可以传递一个复杂的 WHERE 子句,并且它将直接传递到每个数据库操作。

示例

class User extends Eloquent
{
    use \Dozensoftware\Listcraft\Listcraft;

    public function __construct(array $attributes = array(), $exists = false) {

        parent::__construct($attributes, $exists);

        $this->initListcraft([
            'scope' => 'answer_to_ltuae = 42'
        ]);
    }
}

结果为一个作用域

WHERE answer_to_ltuae = 42

###Illuminate\Database\Eloquent\Relations\BelongsTo

如果传递了 Illuminate\Database\Eloquent\Relations\BelongsTo,则 Listcraft 将将作用域的外键与模型实例对应的对应外键的值匹配。

示例

class ToDoListItem extends Eloquent
{
    use \Dozensoftware\Listcraft\Listcraft;

    public function __construct(array $attributes = array(), $exists = false) {

        parent::__construct($attributes, $exists);

        $this->initListcraft([
            'scope' => $this->toDoList()
        ]);
    }

    public function toDoList()
    {
        $this->belongsTo('ToDoList');
    }
}

结果为一个作用域

WHERE to_do_list_id = {{toDoListItem.to_do_list_id 的值}}

###Illuminate\Database\Query\Builder

最后,如果传递了 Illuminate\Database\Query\Builder,则 Listcraft 将提取构建器的 WHERE 子句并将其用作 Listcraft 项目的范围。添加这种作用域类型是为了在 acts_as_list 版本和 Listcraft 之间保持一致性;然而,由于语言和 ActiveRecord 与 Eloquent 之间的差异,这只是一个有限的实现,需要改进以更加灵活和安全。这是一个很大的限制,将在未来的版本中首先解决。

这很棘手,因为它要正常工作,查询对象 where 数组在 PDO 之外准备好绑定,然后作为原始字符串传递。所以,请记住,如果你不仔细构建对象,这种途径可能会让您的应用程序容易受到滥用。如果您使用直接的用户输入,请在将其用作 Listcraft 的作用域之前清理数据。

示例

class ToDoListItem extends Eloquent
{
    use \Dozensoftware\Listcraft\Listcraft;

    public function __construct(array $attributes = array(), $exists = false) {

        parent::__construct($attributes, $exists);

        $this->initListcraft([
            'scope' => DB::table($this->getTable())->where('type', '=', 'Not A List of My Favorite Porn Videos')
        ]);
    }
}

结果为一个作用域

to_do_list_items.type = 'Not A List of My Favorite Porn Videos'

更改配置

您还可以在运行时使用 $this->setListcraftConfig('key', 'value'); 修改任何配置值。例如,要更改作用域,您可以这样做

$this->setListcraftConfig('scope', 'what_does_the_fox_say = "ring ding ding ding"');

在处理更新时,将使用原始作用域从该列表中删除记录,并将其插入到新列表作用域中。请注意。在处理过程中更改配置可能会产生不可预测的效果。

注意

在特质方法中的所有 position 查询(选择、更新等)都将在默认作用域之外执行,这可以防止默认作用域与 Listcraft 作用域不同时出现的问题。

position 列是在调用验证之后设置的,因此你不应该在 position 列上放置 presence 验证。

未来计划

  • 支持使用闭包作为作用域
  • 更新 Illuminate\Database\Query\Builder 作用域以更安全、更灵活
  • 安装命令的附加功能。例如
    • 自动更新模型(包括构造函数中的 init 方法)
    • 生成(或添加)控制器,包括为每个 Listcraft 公共方法创建操作,包括添加必要的路由。这将使得像 https://:8000/foos/1/move_lower 这样的操作变得容易,通过 AJAX-y 前端调用。

除此之外,我希望能根据需要与 Ruby gem acts_as_list 保持一致(https://github.com/swanandp/acts_as_list)。

Listcraft 做贡献

  • 检查最新主分支,以确保功能尚未实现或错误尚未修复
  • 请检查问题跟踪器以确保没有人已经请求或贡献过该问题
  • 分叉项目
  • 创建一个功能/错误修复分支
  • 提交并推送,直到你对你的贡献满意
  • 请确保为它添加测试。这很重要,这样我就不会在未来的版本中无意中破坏它。
  • 请尽量不要修改Composer.json、版本或历史记录。如果你想要自己的版本,或者有其他必要的情况,那是可以的,但请将其隔离到自己的提交中,这样我就可以在它周围选择性地应用更改。
  • 我建议在提交请求之前,使用Laravel 5.0及更高版本测试构建。

版权

版权所有(c)2013-2017 Travis Vignon,遵照MIT许可证发布