Why would you set `null: false, default: ""` on a required DB column?

Viewed 2766

I'm building a Rails app with Devise for authentication, and its default DB migration sets the following columns:

## Database authenticatable
t.string :email,              null: false, default: ""
t.string :encrypted_password, null: false, default: ""

What is the purpose of setting null: false and default: "" at the same time?

My understanding is that null: false effectively makes a value required: i.e., trying to save a record with a NULL value in that column will fail on the database level, without depending any validations on the model.

But then default: "" basically undoes that by simply converting NULL values to empty strings before saving.

I understand that for an optional column, you want to reject NULL values just to make sure that all data within that column is of the same type. However, in this case, email and password are decidedly not optional attributes on a user authentication model. I'm sure there are validations in the model to make sure you can't create a user with an empty email address, but why would you set default: "" here in the first place? Does it serve some benefit or prevent some edge case that I haven't considered?

4 Answers

I'm thinking this is here because of MySQL 'strict mode' not allowing you to disallow a null value without providing a default.

From mysql docs: https://dev.mysql.com/doc/refman/8.0/en/data-type-defaults.html

For data entry into a NOT NULL column that has no explicit DEFAULT clause, if an INSERT or REPLACE statement includes no value for the column, or an UPDATE statement sets the column to NULL, MySQL handles the column according to the SQL mode in effect at the time: If strict SQL mode is enabled, an error occurs for transactional tables and the statement is rolled back. For nontransactional tables, an error occurs, but if this happens for the second or subsequent row of a multiple-row statement, the preceding rows are inserted. If strict mode is not enabled, MySQL sets the column to the implicit default value for the column data type.

Related