The native trash bin is removed from the sheet form, list and kanban views. Sheets are deleted from the **Delete Sheet** button in the header of the sheet form, or from the **Action** menu of the list view for several sheets at once. Both open a confirmation wizard that lists the sheets, the number of timesheet entries and the total number of hours that will be deleted, and a time off section that depends on the configured policy. Nothing is deleted until **Delete permanently** is pressed, and the button is hidden when something blocks the deletion. A plain ``sheet.unlink()`` from a script or a server action raises a ``UserError`` that points to the button, so the confirmation step cannot be skipped by accident. Code that really means to delete does ``sheet._with_delete_cascade().unlink()``. The cascade is armed by a sentinel object rather than by a plain value in the context, and ``_with_delete_cascade()`` is the only way to obtain it. The context of an RPC call is controlled by the caller, so a context flag holding a JSON value could be forged by any authenticated user and would delete a sheet without ever showing the confirmation; a sentinel compared by identity cannot be produced by a deserializer, and a method whose name starts with an underscore cannot be reached remotely. With the ``Cancel the time off`` policy, cancelling a time off request posts a message in its chatter telling the employee that the request has been refused. The wording talks about a refusal, not about a deleted timesheet sheet.