Back to ApiController class

Method save

protected int
save
(mixed $recordKey = null)
Method to save a record.
Parameters
  • int $recordKey The primary key of the item (if exists)
Returns
  • int The record ID on success, false on failure
Since
  • 4.0.0
Class: ApiController
Project: Joomla

Method save - Source code

/**
 * Method to save a record.
 *
 * @param   integer  $recordKey  The primary key of the item (if exists)
 *
 * @return  integer  The record ID on success, false on failure
 *
 * @since   4.0.0
 */
protected function save($recordKey = null)
{
    /** @var \Joomla\CMS\MVC\Model\AdminModel $model */
    $model = $this->getModel(Inflector::singularize($this->contentType));
    if (!$model) {
        throw new \RuntimeException(Text::_('JLIB_APPLICATION_ERROR_MODEL_CREATE'));
    }
    try {
        $table = $model->getTable();
    } catch (\Exception $e) {
        throw new \RuntimeException($e->getMessage());
    }
    $key = $table->getKeyName();
    $data = $this->input->get('data', json_decode($this->input->json->getRaw(), true), 'array');
    $checkin = property_exists($table, $table->getColumnAlias('checked_out'));
    $data[$key] = $recordKey;
    if ($this->input->getMethod() === 'PATCH') {
        if ($recordKey && $table->load($recordKey)) {
            $fields = $table->getFields();
            foreach ($fields as $field) {
                if (array_key_exists($field->Field, $data)) {
                    continue;
                }
                $data[$field->Field] = $table->{$field->Field};
            }
        }
    }
    $data = $this->preprocessSaveData($data);
    // @todo: Not the cleanest thing ever but it works...
    Form::addFormPath(JPATH_COMPONENT_ADMINISTRATOR . '/forms');
    // Needs to be set because com_fields needs the data in jform to determine the assigned catid
    $this->input->set('jform', $data);
    // Validate the posted data.
    $form = $model->getForm($data, false);
    if (!$form) {
        throw new \RuntimeException(Text::_('JLIB_APPLICATION_ERROR_FORM_CREATE'));
    }
    // Test whether the data is valid.
    $validData = $model->validate($form, $data);
    // Check for validation errors.
    if ($validData === false) {
        $errors = $model->getErrors();
        $messages = [];
        // Push up to three validation messages out to the user.
        for ($i = 0, $n = \count($errors); $i < $n && $i < 3; $i++) {
            if ($errors[$i] instanceof \Exception) {
                $messages[] = "{$errors[$i]->getMessage()}";
            } else {
                $messages[] = "{$errors[$i]}";
            }
        }
        throw new InvalidParameterException(implode("\n", $messages));
    }
    if (!isset($validData['tags'])) {
        $validData['tags'] = array();
    }
    // Attempt to save the data.
    if (!$model->save($validData)) {
        throw new Exception\Save(Text::sprintf('JLIB_APPLICATION_ERROR_SAVE_FAILED', $model->getError()));
    }
    try {
        $modelName = $model->getName();
    } catch (\Exception $e) {
        throw new \RuntimeException($e->getMessage());
    }
    // Ensure we have the record ID in case we created a new article
    $recordId = $model->getState($modelName . '.id');
    if ($recordId === null) {
        throw new Exception\CheckinCheckout(Text::sprintf('JLIB_APPLICATION_ERROR_CHECKIN_FAILED', $model->getError()));
    }
    // Save succeeded, so check-in the record.
    if ($checkin && $model->checkin($recordId) === false) {
        throw new Exception\CheckinCheckout(Text::sprintf('JLIB_APPLICATION_ERROR_CHECKIN_FAILED', $model->getError()));
    }
    return $recordId;
}