Reputation:
I currently have a table of image links associate with another model as follows
+----+-------------+----------------+
| id | property_id | url |
+----+-------------+----------------+
| 1 | 2 | /example.jpg |
| 2 | 7 | /example-2.jpg |
| 3 | 5 | /example-3.jpg |
+----+-------------+----------------+
I would like to add a column to the table to order the images as follows
+----+-------------+----------------+------------+
| id | property_id | url | sort_order |
+----+-------------+----------------+------------+
| 1 | 2 | /example.jpg | 1 |
| 2 | 7 | /example-2.jpg | 1 |
| 3 | 2 | /example-3.jpg | 2 |
+----+-------------+----------------+------------+
Is there way to make a database level constraint (i.e. put it in the migration) that the sort_order value auto_increments but is dependent on the propery_id value, such that the sort_order value is essentially an index with each property_id having it's own index?
Upvotes: 3
Views: 1122
Reputation: 2871
<table_name>
should be replaced with your table name.
The key is in this line
\DB::unprepared('CREATE TRIGGER <table_name>_sort_order BEFORE INSERT ON <table_name> FOR EACH ROW SET NEW.sort_order = (SELECT IFNULL(MAX(sort_order), 0) FROM <table_name> WHERE property_id = NEW.property_id) + 1;');
<?php
use Illuminate\Database\Migrations\Migration;
class AddSortOrderTo<table_name_camelized> extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::table(<table_name>, function(Blueprint $table) {
$table->unsignedInteger('sort_order')->default(0);
});
\DB::unprepared('CREATE TRIGGER <table_name>_sort_order BEFORE INSERT ON <table_name> FOR EACH ROW SET NEW.sort_order = (SELECT IFNULL(MAX(sort_order), 0) FROM <table_name> WHERE property_id = NEW.property_id) + 1;');
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
\DB::statement('DROP TRIGGER <table_name>_sort_order');
Schema::table(<table_name>, function (Blueprint $table) {
$table->dropColumn('sort_order');
});
}
}
Upvotes: 1