Тут речь будет о том как контролировать ввод данных в таблицу данных , реализованных на QTableView и QSqlTableModel.
Есть такое предположение, что наиболее правильным подходом будет переопределение класса QSqlTableModel и класса QTableView.
Попытка связать сигнал dataChanged у QTableView или аналогичный у QSqlTableModel будет ошибочной идеей , так как в dataChanged приходит событие, когда уже ничего не изменить.
Тоже можно сказать и о beforeUpdate, в котором в общем-то уже контроллировать нечего и данные записываются в базу.

QTableView
Мы исходим из того , что все действия иницируются руками пользователя, то есть интерактивно, в нашем случае из QTableView.
Есть три варианта действий с таблицей : создание новой строки таблицы (или копирование строки) , удаление строки и редактирование строки, а именно конкретного поля строки.
Копирование строки
Надо сразу отмести функцию insertRecord по той причине, что на вход ей передается QSqlRecord, у которого могут быть Relation поля, то есть внешние связи к другим таблицам.
Так вот в этом поле будет текстовая замена из внешней таблицы , а нам надо получать id поля. И это будет тупиковая ситуация. Если только делать свой форк PblTableView.
Далее остается функция insertRow() и это правильное начало, но она только инициирует начало создания новой строки.
Далее происходит первый вызов setData для какого-нибудь поля .
Если стратегия модели в данный момент onFieldChange, то тут же происходит скрытый submit и возникает updateRow.
Если стратегия модели onRowChanged то можно устанавливать всем полям значения через setData, они помещаются в editBuffer, submit будет вызываться автоматом в коде исходников Qt .
Когда используют разные стратегии модели данных.
submitAll производит запись в базу данных через QSqlQueryModel, это ранний родитель у QSqlTableModel.
Надо понимать, что все в результате идет через обычные sql запросы.
И после submitAll возникает insertRowIntoTable, где уже пошел запрос insert row к базе и контроллировать значения уже поздно.
Таким образом контроль должен реализовываться в setData. В setData проверяем значение поля на валидность и возвращаем либо true, либо false.
Также в зависимости от значения поля 1 тут же в setData можно вызвать setData поля 2. И это нормально работает.