mirror of
https://github.com/alextselegidis/easyappointments.git
synced 2024-11-15 04:22:25 +03:00
Sorting with known previous sibling's ID
This commit is contained in:
parent
0b0c89ba3c
commit
066e9eb236
5 changed files with 67 additions and 94 deletions
|
@ -244,29 +244,21 @@ class Services extends EA_Controller {
|
|||
{
|
||||
abort(400,'Invalid ID value');
|
||||
}
|
||||
$newOrder = request('new_order');
|
||||
if ( (($newOrder = filter_var($newOrder,FILTER_VALIDATE_INT)) === FALSE) ||
|
||||
$newOrder < 0)
|
||||
|
||||
$insertAfterId = request('after');
|
||||
if (($insertAfterId = filter_var($insertAfterId,FILTER_VALIDATE_INT)) === FALSE)
|
||||
{
|
||||
abort(400,'Invalid new order value');
|
||||
abort(400,'Invalid after value, must be ID or -1');
|
||||
}
|
||||
|
||||
$visibleServices = request('allIds');
|
||||
if (empty($visibleServices))
|
||||
if ($insertAfterId <= 0)
|
||||
{
|
||||
abort('allIds must be defined to successfully sort services');
|
||||
$insertAfterId = FALSE;
|
||||
}
|
||||
if (!is_array($visibleServices))
|
||||
{
|
||||
$visibleServices = Array($visibleServices);
|
||||
}
|
||||
|
||||
$visibleServices = array_filter(filter_var_array($visibleServices, FILTER_VALIDATE_INT));
|
||||
|
||||
|
||||
$service = $this->services_model->find($service_id);
|
||||
|
||||
$service['row_order'] = $this->services_model->set_service_order($service['id'], $newOrder,$visibleServices);
|
||||
$service['row_order'] = $this->services_model->set_service_order($service['id'], $insertAfterId);
|
||||
|
||||
return json_response($service);
|
||||
}
|
||||
|
|
|
@ -238,83 +238,53 @@ class EA_Model extends CI_Model {
|
|||
|
||||
|
||||
/**
|
||||
* Inserts entry to desired order in table relative to user visible entries
|
||||
* Inserts entry order after defined entry
|
||||
*
|
||||
* @param string $table Table
|
||||
* @param array $entry Entity
|
||||
* @param int $desiredOrder Desired place in table (relative to visible entities)
|
||||
* @param Array [$visibleIds] Visible ids to sort on
|
||||
* @param string [$order_column] Ordering Column name
|
||||
* @param array $entry Entity to insert
|
||||
* @param mixed|bool $afterId ID of entry where to insert at. Or false to set at beginning
|
||||
* @param string [$order_column] Ordering Column name (Default: row_order)
|
||||
*
|
||||
* @throws RuntimeException
|
||||
* @throws InvalidArgumentException
|
||||
*/
|
||||
|
||||
public function insert_row_order_visible (string $table, array &$entry, int $desiredOrder, Array &$visibleIds = NULL, string $order_column='row_order')
|
||||
public function insert_row_order_after(string $table, array &$entry, $afterId, string $order_column='row_order')
|
||||
{
|
||||
if (empty($table))
|
||||
throw new InvalidArgumentException("Table parameter must be defined");
|
||||
if (empty($column))
|
||||
if (empty($order_column))
|
||||
throw new InvalidArgumentException("Column parameter must be defined");
|
||||
|
||||
if (!array_key_exists('id', $entry))
|
||||
throw new InvalidArgumentException('Entry does not contain ID column');
|
||||
if (!array_key_exists($column,$entry))
|
||||
if (!array_key_exists($order_column,$entry))
|
||||
throw new InvalidArgumentException('Entry does not contain sorting column');
|
||||
|
||||
$setOrder = $desiredOrder;
|
||||
$id = $entry['id'];
|
||||
|
||||
// Get position of desired entry:
|
||||
if (is_int($afterId) && $afterId > 0)
|
||||
{
|
||||
$position = $this->db->from($table)
|
||||
->select([$order_column])
|
||||
->where('id',$afterId)
|
||||
->get()
|
||||
->row_array();
|
||||
if ($position === false)
|
||||
{
|
||||
throw new InvalidArgumentException("Could not found service with ID $afterId");
|
||||
}
|
||||
$position = intval($position[$order_column]);
|
||||
}
|
||||
else {
|
||||
$position = FALSE;
|
||||
}
|
||||
|
||||
if (!empty($visibleIds))
|
||||
{
|
||||
// Set order to reflect real position in DB
|
||||
if (! $this->insert_row_order($table,$entry,$position,$order_column))
|
||||
{
|
||||
throw new RuntimeException('Could not update order, database error');
|
||||
}
|
||||
|
||||
$allRows = $this->db->from($table)
|
||||
->order_by($order_column)
|
||||
->select(['id'])
|
||||
->get()
|
||||
->result_array();
|
||||
if ($desiredOrder >= count($visibleIds) -1)
|
||||
{
|
||||
$setOrder = count($allRows); // Desired last
|
||||
}
|
||||
else {
|
||||
|
||||
for ($i=0; $i < count($allRows); $i++)
|
||||
{
|
||||
if ($i >= count($visibleIds))
|
||||
{
|
||||
break;
|
||||
}
|
||||
elseif ($i > $desiredOrder)
|
||||
{
|
||||
break;
|
||||
}
|
||||
elseif (!in_array($allRows[$i]['id'], $visibleIds))
|
||||
{
|
||||
$setOrder ++;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
$currentOrder = intval(
|
||||
$this->db
|
||||
->select($order_column)
|
||||
->from($table)
|
||||
->where(['id'=>$id])
|
||||
->limit(1)
|
||||
->get()
|
||||
->row_array()
|
||||
[$order_column]
|
||||
);
|
||||
|
||||
if ($setOrder != $currentOrder)
|
||||
{
|
||||
if (! $this->insert_row_order($table,$entry,$setOrder))
|
||||
{
|
||||
throw new RuntimeException('Could not update order, database error');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
@ -323,13 +293,14 @@ class EA_Model extends CI_Model {
|
|||
*
|
||||
* @param string $table Table
|
||||
* @param array $entry Entry, should be associative array containing columns 'Id' and desired $column sort value.
|
||||
* @param int|bool $position Position to set entry to. If set to False, it will be positioned to first.
|
||||
* @param string $column Column name that contains sorting data (default is 'row_order').
|
||||
*
|
||||
* @return bool TRUE on success, FALSE on failure
|
||||
* @throws InvalidArgumentException
|
||||
*/
|
||||
|
||||
protected function insert_row_order(string $table, array &$entry, int $position, string $column = 'row_order')
|
||||
protected function insert_row_order(string $table, array &$entry, $position, string $column = 'row_order')
|
||||
{
|
||||
if (empty($table))
|
||||
throw new InvalidArgumentException("Table parameter must be defined");
|
||||
|
@ -341,8 +312,16 @@ class EA_Model extends CI_Model {
|
|||
if (!array_key_exists($column,$entry))
|
||||
throw new InvalidArgumentException('Entry does not contain sorting column');
|
||||
|
||||
$movingUp = $position >= intval($entry[$column]);
|
||||
$newOr = $movingUp? $position +1 : $position;
|
||||
|
||||
if (is_int($position))
|
||||
{
|
||||
$newOr = $position +1;
|
||||
}
|
||||
else
|
||||
{
|
||||
$newOr = 0;
|
||||
}
|
||||
|
||||
$this->db->update($table, [$column => $newOr ], [ 'id'=> $entry['id'] ]);
|
||||
|
||||
|
||||
|
|
|
@ -542,17 +542,16 @@ class Services_model extends EA_Model {
|
|||
* Sort service
|
||||
*
|
||||
* @param int $service_id Service ID
|
||||
* @param int $desiredOrder Desired place in table (relative to visible services)
|
||||
* @param Array [$allServiceIds] Visible service ids to sort on
|
||||
* @param int|bool $afterServiceId ID of service that service should be inserted after, or FALSE to set to beginning
|
||||
*
|
||||
* @return int New place in table
|
||||
*/
|
||||
|
||||
public function set_service_order(int $service_id, int $desiredOrder, Array &$allServiceIds = NULL)
|
||||
public function set_service_order(int $service_id, $afterServiceId)
|
||||
{
|
||||
$service = $this->find($service_id);
|
||||
|
||||
$this->insert_row_order_visible('services',$service,$desiredOrder,$allServiceIds);
|
||||
$this->insert_row_order_after('services',$service,$afterServiceId);
|
||||
|
||||
return $this->value($service['id'],'row_order');
|
||||
}
|
||||
|
|
|
@ -127,20 +127,17 @@ App.Http.Services = (function () {
|
|||
*
|
||||
* @param {Number} serviceId
|
||||
*
|
||||
* @param {Number} newOrder
|
||||
*
|
||||
* @param {Array} allIds
|
||||
* @param {Number} afterId
|
||||
*
|
||||
* @return {Object}
|
||||
*/
|
||||
function sort(serviceId, newOrder, allIds)
|
||||
function sort(serviceId, afterId)
|
||||
{
|
||||
const url = App.Utils.Url.siteUrl('services/sort');
|
||||
const data = {
|
||||
csrf_token: vars('csrf_token'),
|
||||
service_id: serviceId,
|
||||
new_order : newOrder,
|
||||
allIds
|
||||
after : afterId
|
||||
};
|
||||
return $.post(url,data);
|
||||
}
|
||||
|
|
|
@ -95,7 +95,13 @@ App.Pages.Services = (function () {
|
|||
$services.find('.results').sortable({
|
||||
update: function(ev,ui){
|
||||
resetForm();
|
||||
sort(ui.item.data('id'),ui.item.index())
|
||||
var afterId;
|
||||
if (ui.item.index( )== 0)
|
||||
afterId = -1;
|
||||
else {
|
||||
afterId = ui.item.prev('.service-row').data('id');
|
||||
}
|
||||
sort(ui.item.data('id'), afterId)
|
||||
.catch(err => {
|
||||
$(this).sortable('cancel');
|
||||
$services.find('.form-message').addClass('alert-danger').text(lang('error')).show();
|
||||
|
@ -228,13 +234,13 @@ App.Pages.Services = (function () {
|
|||
*
|
||||
* @param {Number} serviceId Id of service to sort
|
||||
*
|
||||
* @param {Number} newOrder New place in order
|
||||
* @param {Number} afterId Id of service to place after
|
||||
*
|
||||
* @return {Promise<Number>}
|
||||
*/
|
||||
function sort(serviceId, newOrder){
|
||||
return App.Http.Services.sort(serviceId,newOrder,
|
||||
$services.find('.results > .service-row').map((i,e)=> e.dataset['id']).get())
|
||||
function sort(serviceId, afterId){
|
||||
|
||||
return App.Http.Services.sort(serviceId, afterId)
|
||||
.then(response => {
|
||||
App.Layouts.Backend.displayNotification(lang('service_saved'));
|
||||
return response.row_order;
|
||||
|
|
Loading…
Reference in a new issue