The goal is to set a default counter, but let people override it. The counter should be the biggest value of the field plus 1.
Using an event subscriber, FORM ALTER event.
public static function getSubscribedEvents(): array {
return [
HookEventDispatcherInterface::FORM_ALTER => 'setDefaultCbid',
HookEventDispatcherInterface::ENTITY_PRE_SAVE => 'checkCbiRaceCondition'
];
}
public function setDefaultCbid(FormAlterEvent $event) {
$form_id = $event->getFormId();
if ($form_id !== 'node_bond_edit_form') {
return;
}
$result = \Drupal::database()
->query('select max(field_bond_cbid_value) from {node__field_bond_cbid}')
->fetchField();
if ($result) {
$cbid = $result + 1;
}
else {
$cbid = 1;
}
$form = &$event->getForm();
$form_already_alterered = false;
if (array_key_exists('field_bond_cbid_default', $form)) {
$form_already_alterered = TRUE;
}
$form['field_bond_cbid_default'] = [
'#title' => $this->t('default cbid'),
'#type' => 'number',
'#value' => $cbid,
];
if (!$form_already_alterered) {
$form['field_bond_cbid']['widget'][0]['value']['#default_value'] = $cbid;
}
}
This works fine. The value is set and the "default" field visible in the adjusted form
What happens if a second person edits another node and increments the counter whINCORRECTCODEile the form is displayed? This is where field_bond_cbid_default is not available on the entity
public function checkCbiRaceCondition(EntityPresaveEvent $event) {
$bond = $event->getEntity();
if ($bond->bundle() !== 'bond') {
return;
}
$enteredValue = $bond->get('field_bond_cbid')->getString();
$defaultCbid = $bond->get('field_bond_cbid_default')->getString();
if ($enteredValue != $defaultCbid) {
How do I access the default value?