Allow reordering extra keys with drag and drop #2526

This commit is contained in:
Kijin Sung 2025-05-22 21:20:59 +09:00
parent 82fa67be5b
commit a1e5a51b06
8 changed files with 260 additions and 33 deletions

View file

@ -49,6 +49,7 @@
<action name="procDocumentAdminInsertExtraVar" type="controller" permission="manager:config:*" check_var="module_srl" ruleset="insertExtraVar" />
<action name="procDocumentAdminDeleteExtraVar" type="controller" permission="manager:config:*" check_var="module_srl" />
<action name="procDocumentAdminMoveExtraVar" type="controller" permission="manager:config:*" check_var="module_srl" />
<action name="procDocumentAdminReorderExtraVars" type="controller" permission="manager:config:*" check_var="module_srl" />
<action name="procDocumentAdminRecalculateCategoryCounts" type="controller" />
</actions>
<eventHandlers>

View file

@ -246,29 +246,50 @@ class DocumentAdminController extends Document
$type = Context::get('type');
$module_srl = Context::get('module_srl');
$var_idx = Context::get('var_idx');
if (!$type || !$module_srl || !$var_idx)
{
throw new Rhymix\Framework\Exceptions\InvalidRequest;
}
if(!$type || !$module_srl || !$var_idx) throw new Rhymix\Framework\Exceptions\InvalidRequest;
$module_info = ModuleModel::getModuleInfoByModuleSrl($module_srl);
if (!$module_info || !$module_info->module_srl)
{
throw new Rhymix\Framework\Exceptions\TargetNotFound;
}
$oModuleModel = getModel('module');
$module_info = $oModuleModel->getModuleInfoByModuleSrl($module_srl);
if(!$module_info->module_srl) throw new Rhymix\Framework\Exceptions\InvalidRequest;
$extra_keys = DocumentModel::getExtraKeys($module_srl);
if (!$extra_keys)
{
throw new Rhymix\Framework\Exceptions\TargetNotFound;
}
if (!$extra_keys[$var_idx])
{
throw new Rhymix\Framework\Exceptions\InvalidRequest;
}
$oDocumentModel = getModel('document');
$extra_keys = $oDocumentModel->getExtraKeys($module_srl);
if(!$extra_keys[$var_idx]) throw new Rhymix\Framework\Exceptions\InvalidRequest;
if($type == 'up') $new_idx = $var_idx-1;
else $new_idx = $var_idx+1;
if($new_idx<1) throw new Rhymix\Framework\Exceptions\InvalidRequest;
$new_idx = ($type === 'up') ? $var_idx - 1 : $var_idx + 1;
if ($new_idx < 1)
{
throw new Rhymix\Framework\Exceptions\InvalidRequest;
}
$args = new stdClass();
$args->module_srl = $module_srl;
$args->var_idx = $new_idx;
$output = executeQuery('document.getDocumentExtraKeys', $args);
if (!$output->toBool()) return $output;
if (!$output->data) throw new Rhymix\Framework\Exceptions\InvalidRequest;
if (!$output->toBool())
{
return $output;
}
if (!$output->data)
{
throw new Rhymix\Framework\Exceptions\InvalidRequest;
}
unset($args);
$oDB = DB::getInstance();
$oDB->begin();
// update immediately if there is no idx to change
if(!$extra_keys[$new_idx])
{
@ -277,11 +298,19 @@ class DocumentAdminController extends Document
$args->var_idx = $var_idx;
$args->new_idx = $new_idx;
$output = executeQuery('document.updateDocumentExtraKeyIdx', $args);
if(!$output->toBool()) return $output;
if (!$output->toBool())
{
$oDB->rollback();
return $output;
}
$output = executeQuery('document.updateDocumentExtraVarIdx', $args);
if(!$output->toBool()) return $output;
// replace if exists
if (!$output->toBool())
{
$oDB->rollback();
return $output;
}
}
// replace if exists
else
{
$args = new stdClass();
@ -289,25 +318,174 @@ class DocumentAdminController extends Document
$args->var_idx = $new_idx;
$args->new_idx = -10000;
$output = executeQuery('document.updateDocumentExtraKeyIdx', $args);
if(!$output->toBool()) return $output;
if (!$output->toBool())
{
$oDB->rollback();
return $output;
}
$output = executeQuery('document.updateDocumentExtraVarIdx', $args);
if(!$output->toBool()) return $output;
if (!$output->toBool())
{
$oDB->rollback();
return $output;
}
$args->var_idx = $var_idx;
$args->new_idx = $new_idx;
$output = executeQuery('document.updateDocumentExtraKeyIdx', $args);
if(!$output->toBool()) return $output;
if (!$output->toBool())
{
$oDB->rollback();
return $output;
}
$output = executeQuery('document.updateDocumentExtraVarIdx', $args);
if(!$output->toBool()) return $output;
if (!$output->toBool())
{
$oDB->rollback();
return $output;
}
$args->var_idx = -10000;
$args->new_idx = $var_idx;
$output = executeQuery('document.updateDocumentExtraKeyIdx', $args);
if(!$output->toBool()) return $output;
if (!$output->toBool())
{
$oDB->rollback();
return $output;
}
$output = executeQuery('document.updateDocumentExtraVarIdx', $args);
if(!$output->toBool()) return $output;
if (!$output->toBool())
{
$oDB->rollback();
return $output;
}
}
$oDB->commit();
Rhymix\Framework\Cache::delete("site_and_module:module_document_extra_keys:$module_srl");
}
/**
* Reorder extra vars of a module.
*/
public function procDocumentAdminReorderExtraVars()
{
// Validate input data.
$module_srl = intval(Context::get('module_srl'));
$order = Context::get('order');
if (!$module_srl || !$order || !is_array($order))
{
throw new Rhymix\Framework\Exceptions\InvalidRequest;
}
foreach ($order as $key => $val)
{
$order[$key] = $val = (object)$val;
if (empty($val->eid))
{
throw new Rhymix\Framework\Exceptions\InvalidRequest;
}
}
// Validate module info and existing extra keys.
$module_info = ModuleModel::getModuleInfoByModuleSrl($module_srl);
if (!$module_info || !$module_info->module_srl)
{
throw new Rhymix\Framework\Exceptions\TargetNotFound;
}
$extra_keys = DocumentModel::getExtraKeys($module_srl);
if (!$extra_keys)
{
throw new Rhymix\Framework\Exceptions\TargetNotFound;
}
$extra_keys = array_combine(array_map(function($item) {
return $item->eid;
}, $extra_keys), array_values($extra_keys));
// Calculate changes.
// We don't actually do anything with the submitted values of old/new idx.
// We calculate them anew with the data we have on the server.
$changes = [];
$i = 1;
foreach ($order as $key => $val)
{
if (!isset($extra_keys[$val->eid]))
{
continue;
}
if ($i != $extra_keys[$val->eid]->idx)
{
$changes[] = [
'eid' => $val->eid,
'old_idx' => $extra_keys[$val->eid]->idx,
'new_idx' => $i,
];
}
$i++;
}
// Begin transaction.
$oDB = DB::getInstance();
$oDB->begin();
// Apply changes.
// We need to do this twice because of the unique constraint.
foreach ($changes as $change)
{
$output = executeQuery('document.updateDocumentExtraKeyIdxByEid', [
'module_srl' => $module_srl,
'eid' => $change['eid'],
'var_idx' => $change['old_idx'],
'new_idx' => $change['new_idx'] - 10000,
]);
if (!$output->toBool())
{
$oDB->rollback();
return $output;
}
$output = executeQuery('document.updateDocumentExtraVarIdxByEid', [
'module_srl' => $module_srl,
'eid' => $change['eid'],
'var_idx' => $change['old_idx'],
'new_idx' => $change['new_idx'] - 10000,
]);
if (!$output->toBool())
{
$oDB->rollback();
return $output;
}
}
foreach ($changes as $change)
{
$output = executeQuery('document.updateDocumentExtraKeyIdx', [
'module_srl' => $module_srl,
'var_idx' => $change['new_idx'] - 10000,
'new_idx' => $change['new_idx'],
]);
if (!$output->toBool())
{
$oDB->rollback();
return $output;
}
$output = executeQuery('document.updateDocumentExtraVarIdx', [
'module_srl' => $module_srl,
'var_idx' => $change['new_idx'] - 10000,
'new_idx' => $change['new_idx'],
]);
if (!$output->toBool())
{
$oDB->rollback();
return $output;
}
}
// Commit.
$oDB->commit();
// Clear cache.
Rhymix\Framework\Cache::delete("site_and_module:module_document_extra_keys:$module_srl");
}

View file

@ -0,0 +1,13 @@
<query id="updateDocumentExtraKeyIdxByEid" action="update">
<tables>
<table name="document_extra_keys" />
</tables>
<columns>
<column name="var_idx" var="new_idx" notnull="notnull" />
</columns>
<conditions>
<condition operation="equal" column="module_srl" var="module_srl" filter="number" notnull="notnull" />
<condition operation="equal" column="var_idx" var="var_idx" filter="number" notnull="notnull" />
<condition operation="equal" column="eid" var="eid" notnull="notnull" />
</conditions>
</query>

View file

@ -0,0 +1,13 @@
<query id="updateDocumentExtraVarIdxByEid" action="update">
<tables>
<table name="document_extra_vars" />
</tables>
<columns>
<column name="var_idx" var="new_idx" notnull="notnull" />
</columns>
<conditions>
<condition operation="equal" column="module_srl" var="module_srl" filter="number" notnull="notnull" />
<condition operation="equal" column="var_idx" var="var_idx" notnull="notnull" />
<condition operation="equal" column="eid" var="eid" notnull="notnull" />
</conditions>
</query>

View file

@ -110,7 +110,7 @@
<a class="x_btn" href="{getUrl('type','insertExtraForm','selected_var_idx','')}">{$lang->cmd_insert}</a>
</div>
</div>
<table class="x_table x_table-striped x_table-hover">
<table class="x_table x_table-striped x_table-hover sortable extra_keys" data-module-srl="{$module_srl}">
<thead>
<tr class="nowr">
<th>{$lang->no}</th>
@ -123,10 +123,15 @@
<th>&nbsp;</th>
</tr>
</thead>
<tbody>
<tbody class="uDrag">
<block loop="$extra_keys => $key,$val">
<tr>
<td rowspan="2"|cond="$val->desc">{$val->idx}</td>
<tr data-eid="{$val->eid}" data-idx="{$val->idx}">
<td>
<div class="wrap" style="user-select:none">
<button type="button" class="dragBtn">Move to</button>
{$val->idx}
</div>
</td>
<td>{$val->eid}</td>
<td class="nowr"><strong>{$val->name}</strong></td>
<td class="nowr">{$lang->column_type_list[$val->type]}</td>
@ -144,9 +149,6 @@
<button type="button" class="x_icon-trash" onclick="return doDeleteExtraKey('{$module_srl}','{$val->idx}');">{$lang->cmd_delete}</button>
</td>
</tr>
<tr cond="$val->desc">
<td colspan="7">{$val->desc}</td>
</tr>
</block>
</tbody>
</table>

View file

@ -1,5 +1,24 @@
(function($) {
$(function() {
// Reorder extra keys
$('table.extra_keys.sortable').on('after-drag.st', function(e) {
let order = [];
let i = 1;
$(this).find('tbody > tr').each(function() {
order.push({
eid: $(this).data('eid'),
old_idx: parseInt($(this).data('idx'), 10),
new_idx: i++
});
});
Rhymix.ajax('document.procDocumentAdminReorderExtraVars', {
module_srl: $(this).data('moduleSrl'),
order: order
});
});
// Show or hide fields depending on the type of variable
$('select#type').on('change', function() {
const selected_type = $(this).val();
$(this).parents('form').find('.x_control-group').each(function() {
@ -21,5 +40,6 @@
}
});
}).triggerHandler('change');
});
})(jQuery);

View file

@ -23,7 +23,7 @@
<caption>
<strong>{count($group_list)}{$lang->msg_groups_exist}</strong>
<span class="x_pull-right" style="position:relative;top:7px">
{$lang->use_group_image_mark}:
{$lang->use_group_image_mark}:
<label for="yes" class="x_inline"><input type="radio" name="group_image_mark" id="yes" value="Y" checked="checked"|cond="$config->group_image_mark == 'Y'" /> {$lang->cmd_yes}</label>
<label for="no" class="x_inline"><input type="radio" name="group_image_mark" id="no" value="N" checked="checked"|cond="$config->group_image_mark != 'Y'" /> {$lang->cmd_no}</label>
</span>

View file

@ -2206,11 +2206,11 @@ class ModuleModel extends Module
{
$xml_info = self::getModuleActionXml($module_info->module);
}
$xml_grant_list = isset($xml_info->grant) ? (array)$xml_info->grant : array();
$module_grants = self::getModuleGrants($module_info->module_srl)->data ?: [];
// Generate grant
$grant = new Rhymix\Modules\Module\Models\Permission($xml_grant_list, $module_grants, $module_info, $member_info);
$xml_grant_list = isset($xml_info->grant) ? (array)$xml_info->grant : array();
$module_grants = self::getModuleGrants($module_info->module_srl ?? 0)->data ?: [];
$grant = new Rhymix\Modules\Module\Models\Permission($xml_grant_list, $module_grants, $module_info, $member_info ?: null);
return $__cache = $grant;
}