扩展存储在 HTML data-xxx 元素中的对象

Extending object stored in HTML data-xxx element

假设我有以下简化的 HTML 形式:

<form class = 'crud'>
  <div class = 'record' id='record_0'>
    <input id='testa_0' name='testa' class = 'crud-control'>
    <input id='testb_0' name='testb' class = 'crud-control'>
  </div>
  <div class = 'record' id='record_1'>
    <input id='testa_1' name='testa' class = 'crud-control'>
    <input id='testb_1' name='testb' class = 'crud-control'>
  </div>
  <div class = 'record' id='record_2'>
    <input id='testa_2' name='testa' class = 'crud-control'>
    <input id='testb_2' name='testb' class = 'crud-control'>
  </div>
</form>

div.record 元素的 data-update 属性中,我将用户的值 modified/entered 存储在对象 {testa: newvalue, testb: othervalue} 的输入字段中(直到它们被提交到数据库——我在这里跳过提交步骤以减少 code/complexity)。我正在使用 jquery 事件处理程序更新数据更新属性:

  $( 'form.crud, table.crud' ).each(function(i,crud) {

    $(crud).find('.crud-control').change(function() {
      let $record = $($(this).closest( '.record' ));
      $record.data('update',{...$record.data('update'),...{[$(this).attr( 'name' )]:$(this).val()}});
      
    });

  });

此代码有效,但 $record.data('update', ... 看起来有点过于复杂,不是最佳解决方案。有没有更好的方法来扩展带有 key/value 对的 data-xxx 存储对象?

我试过了:

$.extend( $record.data('update'), {[$(this).attr( 'name' )]:$(this).val()})

但是这个 - 出于某种我无法理解的原因 - 更新了 all div.records 的 data-update 属性,而不仅仅是一个 closest()input.crud-control 已更新。

有什么想法吗?

你们非常亲密。如果要创建一个新的对象,基本上就是两者的结合:

$record.data(
    'update',
    // Create a new object
    {
        // Spread out the previous object's properties into it (if any)
        ...$record.data('update'),
        // Add the new property using computed property name syntax
        [$(this).attr( 'name' )]: $(this).val()
    }
);

但是请注意,没有理由$(this).attr('name'),只是使用this.name,它完全是标准的。同样,$(this).val() 对于 input 元素是不必要的,只需 this.value 就足够了。

应用了那些:

$record.data(
    'update',
    // Create a new object
    {
        // Spread out the previous object's properties into it (if any)
        ...$record.data('update'),
        // Add the new property using computed property name syntax
        [this.name]: this.value
    }
);

或者,您可以更新现有对象(如果您使用 jQuery 的 data 方法,它仍然是一个对象,它不会通过文本进行往返) :

const object = $record.data("update") || {};
object[this.name] = this.value;
$record.data("update", object);

如果您 data-update="{}" 到元素的 HTML 标记以便您知道对象将在那里,那么您可以这样做:

$record.data("update")[this.name] = this.value;

同样,由于这是使用 jQuery 的 data(仅从 data-update 属性获取 初始 值,对象存储为对象,而不是文本。