Open MarvinKlein1508 opened 3 years ago
Firebird neither changes nor even checks the stored values when some column is altered. The benefit is that ALTERs are instant and non-blocking. The downside is that only safe conversions are allowed. Changing from NUMERIC(15, 2) to NUMERIC(15, 4) reduces the integral part from 13 to 11 decimal digits and thus the existing values may potentially not fit into the new definition, hence you see an error.
A possible workaround could be to define the column as NUMERIC(17, 4) to compensate the precision loss. Or just create a different column as you already tried.
@dyemanov changing TMONEYLONG
to NUMERIC(17,4)
works and allows me to change the column type. However, all columns needs more storage now which is not necessary in our use case.
Creating a different column doesn't work in our case because the original column as dependencies in many procedures and views.
I think you should allow people to always exchange the datatype of a column when all data within the column is set to NULL. This makes it so much easier for people to change existing columns.
However, all columns needs more storage now which is not necessary in our use case.
No, they doesn't because of records compression.
This makes it so much easier for people to change existing columns.
I personally don't see support for bad database designers as "a good thing".
In both cases storage is the same - 8 bytes per value.
But generally I agree it's worth checking all values for being compatible with the new stricter definition, instead of rejecting this unconditionally. It has a cost -- the whole table must be read -- but perhaps it's acceptable.
the whole table must be read...
"...in exclusive mode" which makes things worse.
But generally I agree it's worth checking all values for being compatible with the new stricter definition, instead of rejecting this unconditionally. It has a cost -- the whole table must be read -- but perhaps it's acceptable.
Only if explicitly required by the user, please. For ex. with extension to the ALTER TABLE syntax to force such a check.
the whole table must be read... "...in exclusive mode" which makes things worse.
PR is enough in this case. Same as when build an index.
I totally agree with you. There should be a method to enable this kind of feature.
In our case we need to update an old Firebird 2.5 database to fit our needs which we didn't know of back in the past.
Our most common changes are the following:
Doing this changes manually is hard for us. Because as mentioned previously, a column might have around 100 dependencies from different procedures, triggers and views. And I don't want to create a new database everytime and migrate all data.
On Wed, 23 Jun 2021 02:22:14 -0700 Dimitry Sibiryakov @.***> wrote:
However, all columns needs more storage now which is not necessary in our use case.
No, they doesn't because of records compression.
This makes it so much easier for people to change existing columns.
I personally don't see support for bad database designers as "a good thing".
We certainly do not want to support bad database design but I suspect in most cases the design was adequate for the requirements of the day and the options available. However times and requirements change. I think all of us must look back and sometimes think 'If I was to do that today I would do things differently.'
Increasing firebird's ability to allow a database design to evolve has to be a good thing for firebird - both to keep existing users and add new ones.
Paul --
Paul Reeves http://www.ibphoenix.com Supporting users of Firebird
I suspect in most cases the design was adequate for the requirements of the day and the options available. However times and requirements change.
Yes, it is natural process but in such cases creation of a new database from scratch for new requirements and pumping data from old one is the best approach that guarantee no problem appear afterward with missed dependencies like variables based on domain or column.
Pumping data with ESonEDS is quite effective as you know.
@aafemt
I don't think creating an enitre new database everytime is super easy to manage. I migrated our last database from FB2.5 to Firebird 4 a few weeks ago. While I did this I changed the encoding from ISO88591 to UTF8. The backup tools etc. were really painful to use for this process so I ended up creating all tables, views, triggers and procedures by hand which took me a around a week. Not to mention that all import tools have failed so I needed to write a custom tool for our data migration.
I don't want to go through this entire process again just to change the type of a column which is compatible by default.
A week? It doesn't sound right. If you have well-organized development, then you have a "master script" for database creation in your version control system. The migration is actually a fork of a new branch in VCS and fixing incompatibilities found during the script's run on new server version. There must be something really wrong if you wasted a whole week on that.
Data migration through Execute Statement on External Data Source is also a script that simply feeds data from old server and inserts into new tables. Its development may be long if you have thousands of tables but as soon as it is complete, running it is a matter of one double-click and can be performed as many times as much errors it encounter without affecting current production server (because test runs are performed on a copy).
PS: I intentionally doesn't mention "smooth migration" with replication usage.
I would relate this to https://groups.google.com/g/firebird-support/c/7YOx9MOw_ts/m/ROIki33IBQAJ "Conversion from base type XXX to YYY is not supported." When Firebird can't convert safely the data, it could allow the user to specify how to do the conversion
To make the previous comment more explicit: Maybe Firebird can add something similar to PostgreSQL's USING
option of their alter column clause (see https://www.postgresql.org/docs/13/sql-altertable.html). This allows you to specify an expression to apply for conversion to the new data type.
This does not fit our ALTER TABLE
architecture. USING
implies the conversion happens during ALTER TABLE
which is true for PGSQL but wrong for Firebird, as we convert the old data type to the new one while reading the field (old record format is converted to the latest one) -- this is why they should be compatible. We may end with three options to consider:
The last option generally kills the major DDL benefit we have as compared to other databases, but perhaps it will find its users.
An alternative would be to enhance the current record conversion system to also be able to apply expressions when migrating from one version to another, but then the next problem is: what if the conversion is invalid.
Why consider these as options and not execution plans? If USING expression is used - UPDATE strategy is forced, if change may be dangerous - CHECK is performed (if confirmation verb used as Vlad suggested), otherwise it works as now.
Don't forget about indices on such column - it should be disabled before explicit conversion and rebuild after. Same about constraints. It is not as easy task as it seems.
I want to change a column type from type
TMONEY
toTMONEYLONG
. This are custom defined domains.However the update always fails with this error message:
When I create a new column of type TMONEYLONG I can insert all data from the other column without any issues. I tried to set the old column to NULL then and then change the column type again but this throws me the same error message as before.