One thing I haven't mentioned about SQLite that makes it simpler to use from Scheme (and requires less machinery in the library) is that it's dynamically typed. Here's a precis of the interaction between the underlying dynamic typing and static SQL column type declarations.
1) All declared column types in CREATE TABLE are reduced to one of four cases: string, integer, numeric, or blob (which should be called "any"). The last is the default if you don't specify a static type.
2) Any column can hold a NULL (except a NOT NULL column, of course) or a blob.
3) Inserting/updating a string column coerces numbers to strings.
4)
Inserting/updating an integer column coerces a string to an integer if it has integer syntax, and a float to an integer if it has an integral value. Everything else is left uncoerced. Exception: an INTEGER PRIMARY KEY column (= ROWID) only accepts integers.
5)
Inserting/updating a numeric column coerces a string to an integer if it has integer syntax and to a float if it has float syntax but not integer syntax. Everything else is left uncoerced .
6)
Inserting/updating an "any" column never coerces anything.
In effect, then, queries will return the column type if what was inserted could be losslessly coerced into that type, but if not, it will return whatever type of object was inserted.