Migrate from SQL Server
Move an existing history database from Microsoft SQL Server to PostgreSQL with TimescaleDB.
This page follows the Documentation PDF, which gives the outline and the Timescale commands. It is a skeleton, not a tested recipe for an Ignition historian, and it was written around a generic table with a column called time.
Read this before you start
- Test on a copy first. Do the whole migration on a copy of the history database, and keep the SQL Server database untouched until the new one has been checked.
- The Ignition tables belong together. The history data refers to tags by
tagid, and the tag list lives insqlth_te, with related tablessqlth_scinfo,sqlth_drv,sqlth_sceandsqlth_partitions(see Maintenance). If data partitioning was on in SQL Server, the history is spread over several data tables, listed insqlth_partitions. Bring all of them over together, or the tag ids will not match. - The PDF's examples use a
timecolumn. Ignition's data table uses a millisecond number int_stamp. Use the hypertable commands from Hypertable setup for it, not the generic ones below.
Steps
-
Install PostgreSQL and TimescaleDB, create the database and connect Ignition, as in Install on Windows or Install on Ubuntu, Database access and steps 1 to 3 of Ignition setup. Do not enable history on any tag yet.
-
Generate a script of the schema from SQL Server. In SQL Server Management Studio, script the tables.
-
Dump the tables (the data) from SQL Server.
-
Load the schema script into PostgreSQL. SQL Server's script syntax is not the same as PostgreSQL's, so expect to fix some of it by hand.
-
Convert the data table to a hypertable. The PDF's generic form is:
For Ignition's
t_stampcolumn use the form from Hypertable setup, step 1, with the millisecond chunk interval andunix_nowfunction. -
Add an index. The PDF's example is
CREATE INDEX ON conditions(time, <column_name>) WITH (timescaledb.transaction_per_chunk);.conditionsis the table name from Timescale's own example, so use your own table. Thetransaction_per_chunksetting makes Timescale build the index chunk by chunk. -
Add compression:
ALTER TABLE <table_name> SET ( timescaledb.compress, timescaledb.compress_segmentby = '<column_name>', timescaledb.compress_orderby = 'time DESC' ); SELECT compress_chunk(c) from show_chunks('<table_name>') c; SELECT add_compression_policy('<table_name>', INTERVAL '8 days');The second statement compresses every existing chunk right away, so the loaded data does not wait for the policy. The
INTERVAL '8 days'form is for a table with a real time-stamp column. For Ignition's millisecond column the age is a number, as in Hypertable setup, step 4. -
Load the dumped data into the new tables.
-
In Ignition, set the storage provider of your tags to the new PostgreSQL database, then re-check history in a trend.
Not covered by the PDF
The PDF does not say how to dump, convert or load the data, or how to carry over Ignition's tag ids. Check the result by comparing row counts and by looking at a known tag's trend before and after.