Trongate Way Docs

Updating and Deleting Records

The update and delete endpoints follow a similar pattern to get_one(): they accept an ID from the URL, verify the record exists, perform the operation, and return an appropriate response.

Updating a Record - PUT

The update() endpoint combines patterns from get_one() (ID extraction, existence check) and create() (JSON parsing, validation):

PHP
public function update(): void {
    $this->authenticate();

    $update_id = segment(3, 'int');

    if ($update_id === 0) {
        http_response_code(400);
        echo json_encode([
            'error' => 'No country ID provided.'
        ]);
        return;
    }

    $existing = $this->model->get_one($update_id);

    if ($existing === false) {
        http_response_code(404);
        echo json_encode([
            'error' => 'Country not found.'
        ]);
        return;
    }

    $data = $this->get_post_data();

    if ($data === null) {
        http_response_code(400);
        echo json_encode([
            'error' => 'Invalid or missing JSON payload.'
        ]);
        return;
    }

    $validation_errors = $this->validate($data);

    if (!empty($validation_errors)) {
        http_response_code(400);
        echo json_encode([
            'error' => 'Validation failed.',
            'fields' => $validation_errors
        ]);
        return;
    }

    $this->model->update($update_id, $data);

    http_response_code(200);
    echo json_encode([
        'message' => 'Country updated successfully.',
        'id' => $update_id,
        'country' => $data
    ]);

    $this->log_request('update', $update_id);
}

The method checks each precondition in order and returns early if any check fails. This is sometimes called the guard clause pattern - validate everything before doing work, and return immediately on the first error.

The Model Update

PHP
public function update(int $update_id, array $data): void {
    $update_data = [
        'country_title' => trim($data['country_title']),
        'country_code' => strtoupper(
            trim($data['country_code'])
        )
    ];

    $this->db->update(
        $update_id, $update_data, 'countries'
    );
}

Deleting a Record - DELETE

The destroy() endpoint is the simplest of the write operations:

PHP
public function destroy(): void {
    $this->authenticate();

    $update_id = segment(3, 'int');

    if ($update_id === 0) {
        http_response_code(400);
        echo json_encode([
            'error' => 'No country ID provided.'
        ]);
        return;
    }

    $existing = $this->model->get_one($update_id);

    if ($existing === false) {
        http_response_code(404);
        echo json_encode([
            'error' => 'Country not found.'
        ]);
        return;
    }

    $this->model->destroy($update_id);

    http_response_code(200);
    echo json_encode([
        'message' => 'Country deleted successfully.'
    ]);

    $this->log_request('destroy', $update_id);
}

200 vs 204 for Deletion

You may have seen REST APIs that return 204 No Content after a successful deletion. There is genuine debate about which is correct. We use 200 in this chapter because we include a confirmation message in the response body, which provides a better developer experience - the client can display "Country deleted successfully" to the user without needing to synthesise their own success message.

If you prefer the purist approach, simply change http_response_code(200) to http_response_code(204) and omit the echo json_encode(...) line. Both are valid.

Testing

BASH
# Update a record
curl -X PUT \
  -H "Trongatetoken: your-token" \
  -H "Content-Type: application/json" \
  -d '{"country_title":"New Name","country_code":"NN"}' \
  http://localhost/countries_api/update/1

# Delete a record
curl -X DELETE \
  -H "Trongatetoken: your-token" \
  http://localhost/countries_api/destroy/1

# Update non-existent record
curl -X PUT \
  -H "Trongatetoken: your-token" \
  -H "Content-Type: application/json" \
  -d '{"country_title":"Nope","country_code":"NP"}' \
  http://localhost/countries_api/update/999

The third test case - attempting to update a record that does not exist - should return 404 Not Found with an informative error message.

We're continually improving the Trongate documentation. If anything is incorrect, unclear, incomplete, or could be better, we'd genuinely appreciate your input.

Share your thoughts in the Documentation Feedback.

Leave Feedback About This Page