Drupal - Update title field in hook_ENTITY_TYPE_insert()

Since nodes have no id on insert, you should just save the node twice.

node_save() initiates a database transaction, in which the changes are not yet written, but the id is already reserved (explaining your issues with not being able to save). You will have to await the database transaction before attempting to save the node again. Unfortunately there is no hook for this.

However, there is a workaround: drupal_register_shutdown_function(). This can be used to call an additional function at the end of the request.

You'll end up with a code like this:

function your_module_node_insert($node){
  if($node->type == 'your_node'){

function _your_module_post_insert($node) {
  if ($node) {

Code comes originally from here:

The presave hook is called before the entity is saved, due to that, it does not yet have an ID. That makes you can not use it, it will be empty (your code there is also wrong, id(), returns an ID, not an object, either ->nid->value, or ->id(), as you have in insert().

The insert hook does have an ID, but it it's after saving. You're updating the object in memory but it is not persisted (again) automatically. You can persist it if you want to, simply by explicitly calling $node->save() again.

However, that obviously has some performance drawbacks (but it is possible, despite what the other answers said) as you have to save everything twice.

My recommendation would simply be to rely on a value that you do know, which is basically everyting except the ID and revision ID. For example the creation date:

$node->title = 'Submission from ' . \Drupal::service('date.formatter')->format($node->getCreatedTime());

in hook_presave() should work fine and give you a title that contains a user readable timestamp.