Scenario
I am developing an internal CakePHP company application that has a despatch screen, which has three lists:
- Available items for despatch (Shown below on the left – “Items Available for Packing”)
- Already packed items pulled from the database (Shown below on the right – “Packed Items”)
- Changes to the packed items list (Form submission after changes have been made)
The user can drag items from the left list to the right list and vice versa. Once the click the Save button, the form is submitted with the items on the right list.

Desired Result
As part of the save, I need to compare (using PHP) the updated list with the saved list from the database.
With any additions, I need to update the items record with the despatch ID.

With any removals, I need to update the items record to sell the despatch ID to NULL.

This would allow users to drag and drop items in both directions, then click Save and expect the page to load with the state they left the page in.
Current State
I am able to save items to be added to the list and, separately, save items being removed. However, I cannot get them working together. When I try this, one item being added to the list completely replace all the other items on the “Packed Items” list.
Code so far…
function edit() {
$this->Despatch->recursive = -1;
if (!empty($this->data)) {
if($this->Despatch->save($this->data)) {
/* NEED TO RETRIEVE CURRENT REPAIR IDs ASSOCIATED
WITH THE DESPATCH ID AND COMPARE WITH FORM SUBMISSION LIST TO
REMOVE THE DIFFERENCES */
# Retrieve current repair records where despatch_id = $this->id.
$this->Despatch->Repair->recursive = -1;
$current_associated_repairs = $this->Despatch->Repair->find('all', array(
'fields' => array('id', 'despatch_date', 'despatch_id'),
'conditions' => array('Repair.despatch_id =' => $this->data['Despatch']['id'])));
# Create array with repair IDs
$repairs = explode(",", $this->data['Repair']['ids']);
$i = 0;
foreach($repairs as $repair) {
$repairupdates[$i]['Repair']['id'] = $repair;
$i++;
}
# Delete array index to prevent it interfering with form saving later
unset($this->data['Repair']['ids']);
# 2. Find unmatched IDs between current records and form submission list of repairs
$length1 = sizeof($current_associated_repairs);
$length2 = sizeof($this->data['Repair']);
for ($i = 0; $i < $length1; $i++) {
for ($j = 0; $j < $length2; $j++) {
### LOGIC NOT CORRECT HERE !!! ###
### THIS WORKS FOR REMOVING PACKED INSTRUMENTS - FROM RIGHT TO LEFT ###
### BUT ACTUALLY BEING TRIGGERED WHEN ADDING FROM LEFT TO RIGHT TOO ###
if ($current_associated_repairs[$i]['Repair']['id'] == $this->data['Repair'][$j]['id']
&& !in_array($current_associated_repairs[$i]['Repair']['id'], $this->data['Repair'][$j])) {
# if it's in current repairs and not in form submission, set to null...
# otherwise, it must be an addition if there's no matches
# 3. Set the despatch_date and despatch_id fields of those records to NULL
$this->data['Repair'][$j+1]['id'] = $current_associated_repairs[$i]['Repair']['id'];
$this->data['Repair'][$j+1]['despatch_date'] = null;
$this->data['Repair'][$j+1]['despatch_id'] = null;
}
}
}
# 4. Save the new list of repairs to the current despatch
if($this->Despatch->save($this->data) && $this->Despatch->Repair->saveAll($this->data['Repair'])) {
$this->Session->setFlash(__('The despatch has been saved.', true), 'default', array('class' => 'success-scheme message'));
} else {
$this->Session->setFlash(__('The repair could not be updated with the despatch number. Please try again.', true), 'default', array('class' => 'error-scheme message'));
}
} else {
$this->Session->setFlash(__('The despatch could not be saved. Please try again.', true), 'default', array('class' => 'error-scheme message'));
}
$this->redirect($this->referer(array('action' => 'view', $this->data['Despatch']['id'])));
}
}
I think I’ve included all the detail anyone should need, but just ask if you need to know more. The main problem I’m having is understanding the logic the code for achieving this.
Many thanks in advance.
PS – JavaScript Code
// click handler for saving despatch - required to save sortable lists properly
$('#save_despatch').click(function(e) {
e.preventDefault();
// gives comma-separated array of instrument IDs, e.g. 12345, 56789...
var result = $('#sortable2').sortable('toArray');
$('#RepairIds').val(result);
$('form').submit();
});
I can not really figure out what you are doing now in your logic, but I will suggest an approach that should work without a doubt.
You have two lists, for simplicity: left and right. This code is sort of pseudocode because I do not fully understand what you need, but this way, the lists should remain updated, and it cant go wrong.
Logic before displaying the lists (in PHP):
JS:
Then on the receiving end: