davidgut/sortable 问题修复 & 功能扩展

解决BUG、新增功能、兼容多环境部署,快速响应你的开发需求

邮箱:yvsm@zunyunkeji.com | QQ:316430983 | 微信:yvsm316

davidgut/sortable

最新稳定版本:v3.1.0

Composer 安装命令:

composer require davidgut/sortable

包简介

A sortable trait for Laravel models

README 文档

README

Drag-and-drop sorting for your Eloquent models — backend and frontend included.
No dependencies, no build step required for the JS, just install and go.

Supports Laravel 11, 12 & 13.

Quick Start

composer require davidgut/sortable

Add a sort_order column to any table you want to sort:

$table->integer('sort_order')->nullable();

Then implement the contract on your model:

use DavidGut\Sortable\Contracts\Sortable;
use DavidGut\Sortable\Traits\SortableTrait;

class Post extends Model implements Sortable
{
    use SortableTrait;
}

That's it for the backend. New records automatically get the next sort order, and the package registers a PUT /sortable/{model}/{id} route for you.

Frontend

Publish the included JavaScript:

php artisan vendor:publish --tag=sortable-assets

Import it in your app.js:

import SortableList from './vendor/sortable/sortable';

SortableList.start();

Mark up your list:

<x-sortable::list>
    @foreach($posts as $post)
        <x-sortable::item :model="$post">
            <x-sortable::drag />
            {{ $post->title }}
        </x-sortable::item>
    @endforeach
</x-sortable::list>

This produces:

<ul data-sortable>
    <li data-sortable-update-url="/sortable/Post/1">
        <span class="drag"></span>
        My First Post
    </li>
    ...
</ul>

All three components accept as to change the rendered element (defaults: ul, li, span), and forward any extra attributes:

<x-sortable::list as="div" class="grid gap-2">
    @foreach($posts as $post)
        <x-sortable::item as="div" :model="$post" class="card">
            <x-sortable::drag as="button" class="cursor-grab"></x-sortable::drag>
            {{ $post->title }}
        </x-sortable::item>
    @endforeach
</x-sortable::list>

Without Components

If you prefer plain HTML, use the @sortableUrl directive or the ->sortableUrl() method:

<ul data-sortable>
    @foreach($posts as $post)
        <li @sortableUrl($post)>
            <span class="drag"></span>
            {{ $post->title }}
        </li>
    @endforeach
</ul>

Make sure you have a <meta name="csrf-token"> tag in your layout — the JS reads it for requests.

Done. Your list is now sortable.

Configuration

Registering Models

Publish the config:

php artisan vendor:publish --tag=sortable-config

Map your models in config/sortable.php:

'models' => [
    'posts' => \App\Models\Post::class,
],

In non-production environments the package will also try to resolve App\Models\{Name} automatically, so you can skip this step during development. In production, only explicitly registered models are allowed.

Custom Sort Column

The default column is sort_order. To change it, set the property on your model:

class Post extends Model implements Sortable
{
    use SortableTrait;

    protected $sortColumn = 'order';
}

Scoped Sorting

Need separate sort orders per group? For example, sorting posts within each category independently:

class Post extends Model implements Sortable
{
    use SortableTrait;

    protected ?string $sortScope = 'category_id';
}

Each category_id will now have its own sort sequence starting from 0.

Custom Sort Queries

For more advanced cases, override sortQuery():

protected function sortQuery(): Builder
{
    return parent::sortQuery()->where('is_active', true);
}

Custom Routes

The package auto-registers routes with web middleware. If you need to customise them:

php artisan vendor:publish --tag=sortable-routes

Query Scope

Retrieve records in sorted order:

Post::sorted()->get();
Post::sorted('desc')->get();

Authorization

By default, only users where $user->isAdmin() returns true can re-sort items. Override this per model:

public function canBeSortedBy($user): bool
{
    return $user->id === $this->user_id;
}

SPA / Livewire

SortableList.start() returns the created instances. Call SortableList.stop() to tear them down on navigation:

const instances = SortableList.start();

// Later, on page leave:
SortableList.stop();

License

MIT

统计信息

  • 总下载量: 3
  • 月度下载量: 0
  • 日度下载量: 0
  • 收藏数: 1
  • 点击次数: 2
  • 依赖项目数: 0
  • 推荐数: 0

GitHub 信息

  • Stars: 1
  • Watchers: 0
  • Forks: 0
  • 开发语言: PHP

其他信息

  • 授权协议: MIT
  • 更新时间: 2025-12-15

承接程序开发

PHP开发

VUE

Vue开发

前端开发

小程序开发

公众号开发

系统定制

数据库设计

云部署

网站建设

安全加固