Getting SQLite metadata with Ruby
last modified July 6, 2020
Metadata is information about the data in a database. Metadata in SQLite contains information about the tables and columns in which we store data. The number of rows that an SQL statement affects is metadata. The number of rows and columns returned in a result set are metadata as well.
Metadata in SQLite can be obtained using the PRAGMA
command.
SQLite objects may have attributes, which are metadata. Finally, we can
also obtain specific metatada from querying the SQLite system
sqlite_master
table.
#!/usr/bin/ruby require 'sqlite3' begin db = SQLite3::Database.open "test.db" pst = db.prepare "SELECT * FROM Cars LIMIT 6" puts pst.columns puts pst.types puts pst.column_count rescue SQLite3::Exception => e puts "Exception occurred" puts e ensure pst.close if pst db.close if db end
In the above example, we get the column names, column types, and the number of columns of a prepared statement.
puts pst.columns puts pst.types puts pst.column_count
These three methods return the column names, column types, and the number of columns of a prepared statement.
$ ./cols_fields.rb Id Name Price INTEGER TEXT INT 3
The output shows three column names: Id
, Name
,
and Price
. The types are INTEGER
, TEXT
,
and INT
.
The following example shows how to retrieve the number of changes produced by a particular SQL command.
#!/usr/bin/ruby require 'sqlite3' begin db = SQLite3::Database.new ":memory:" db.execute "CREATE TABLE Friends(Id INTEGER PRIMARY KEY, Name TEXT)" db.execute "INSERT INTO Friends(Name) VALUES ('Tom')" db.execute "INSERT INTO Friends(Name) VALUES ('Rebecca')" db.execute "INSERT INTO Friends(Name) VALUES ('Jim')" db.execute "INSERT INTO Friends(Name) VALUES ('Robert')" db.execute "INSERT INTO Friends(Name) VALUES ('Julian')" db.execute "DELETE FROM Friends WHERE Id IN (3, 4, 5)" n = db.changes puts "There has been #{n} changes" rescue SQLite3::Exception => e puts "Exception occurred" puts e ensure db.close if db end
We create a Friends table in memory. In the last SQL command, we delete three
rows. We use the changes
method to get the number of changes done
by the last SQL operation.
db.execute "DELETE FROM Friends WHERE Id IN (3, 4, 5)"
In this SQL statement, we delete three rows.
n = db.changes puts "There has been #{n} changes"
We find out the number of changes done by the last SQL statement.
$ ./changes.rb There has been 3 changes
Example output.
In the next example, we will find out some data about the
Cars
table.
#!/usr/bin/ruby require 'sqlite3' begin db = SQLite3::Database.open "test.db" stm = db.prepare "PRAGMA table_info('Cars')" rs = stm.execute rs.each do |row| puts row.join "\s" end rescue SQLite3::Exception => e puts "Exception occurred" puts e ensure stm.close if stm db.close if db end
In this example, we issue the PRAGMA table_info(tableName)
command
to get some metadata info about our Cars table.
stm = db.prepare "PRAGMA table_info('Cars')" rs = stm.execute
The PRAGMA table_info(Cars)
command returns one row for each
column in the Cars table. Columns in the result set include the column order
number, column name, data type, whether or not the column can be
NULL
, and the default value for the column.
rs.each do |row| puts row.join "\s" end
We iterate over the result set and print the data.
$ ./table_info.rb 0 Id INTEGER 0 1 1 Name TEXT 0 0 2 Price INT 0 0
Output of the example.
Next we will print 5 rows from the Cars
table with
their column names.
#!/usr/bin/ruby require 'sqlite3' begin db = SQLite3::Database.open "test.db" rows = db.execute2 "SELECT * FROM Cars LIMIT 5" rows.each do |row| puts "%3s %-8s %s" % [row[0], row[1], row[2]] end rescue SQLite3::Exception => e puts "Exception occurred" puts e ensure db.close if db end
We print five rows of the Cars
table to the console.
Now, we include the names of the columns too. The records are aligned
with the column names.
rows = db.execute2 "SELECT * FROM Cars LIMIT 5"
The execute2
method executes the given SQL statement.
The first row returned is the names of the columns.
rows.each do |row| puts "%3s %-8s %s" % [row[0], row[1], row[2]] end
The data is retrieved, formatted, and printed to the terminal.
$ ./column_names.rb Id Name Price 1 Audi 52642 2 Mercedes 57127 3 Skoda 9000 4 Volvo 29000 5 Bentley 350000
Output.
In our last example related to the metadata, we will
list all tables in the test.db
database.
#!/usr/bin/ruby require 'sqlite3' begin db = SQLite3::Database.open "test.db" rows = db.execute <<SQL SELECT name FROM sqlite_master WHERE type='table' ORDER BY name;" SQL rows.each do |row| puts row end rescue SQLite3::Exception => e puts "Exception occurred" puts e ensure db.close if db end
The code example prints all available tables in the current database to the terminal.
rows = db.execute <<SQL SELECT name FROM sqlite_master WHERE type='table' ORDER BY name;" SQL
The table names are retrieved from the sqlite_master
table.
$ ./list_tables.rb Cars Friends Images
These were the tables on our system.
In this part of the SQLite Ruby tutorial, we have worked with database metadata.