Skip to content

Commit 90288d9

Browse files
committed
Fix docs generation and update README. Should fix #166
1 parent 9a6c8d8 commit 90288d9

File tree

4 files changed

+6
-295
lines changed

4 files changed

+6
-295
lines changed

README.md

Lines changed: 3 additions & 292 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
# SQLite
22

3-
*A Julia interface to the SQLite library.*
3+
*A Julia interface to the [sqlite](https://sqlite.org/index.html) library.*
44

55
| **Documentation** | **PackageEvaluator** | **Build Status** |
66
|:-------------------------------------------------------------------------------:|:---------------------------------------------------------------:|:-----------------------------------------------------------------------------------------------:|
@@ -9,11 +9,7 @@
99

1010
## Installation
1111

12-
The package is registered in `METADATA.jl` and so can be installed with `Pkg.add`.
13-
14-
```julia
15-
julia> Pkg.add("SQLite")
16-
```
12+
The package is registered in the [General registry](https://github.com/JuliaRegistries/General) and so can be installed with `] add SQLite`.
1713

1814
## Documentation
1915

@@ -22,7 +18,7 @@ julia> Pkg.add("SQLite")
2218

2319
## Project Status
2420

25-
The package is tested against Julia `0.6` and `0.7-dev` on Linux, OS X, and Windows.
21+
The package is tested against Julia `1.0` and `nightly` on Linux, OS X, and Windows.
2622

2723
## Contributing and Questions
2824

@@ -51,288 +47,3 @@ Contributions are very welcome, as are feature requests and suggestions. Please
5147
[pkg-0.6-url]: http://pkg.julialang.org/?pkg=SQLite
5248
[pkg-0.7-img]: http://pkg.julialang.org/badges/SQLite_0.7.svg
5349
[pkg-0.7-url]: http://pkg.julialang.org/?pkg=SQLite
54-
55-
## Package Documentation
56-
57-
#### Types/Functions
58-
* `SQLite.DB(file::AbstractString)`
59-
60-
`SQLite.DB` requires the `file` string argument as the name of either a pre-defined SQLite database to be opened, or if the file doesn't exist, a database will be created.
61-
62-
The `SQLite.DB` object represents a single connection to an SQLite database. All other SQLite.jl functions take an `SQLite.DB` as the first argument as context.
63-
64-
To create an in-memory temporary database, call `SQLite.DB()`.
65-
66-
The `SQLite.DB` will automatically closed/shutdown when it goes out of scope (i.e. the end of the Julia session, end of a function call wherein it was created, etc.)
67-
68-
* `SQLite.Stmt(db::SQLite.DB, sql::String)`
69-
70-
Constructs and prepares (compiled by the SQLite library) an SQL statement in the context of the provided `db`. Note the SQL statement is not actually executed, but only compiled (mainly for usage where the same statement is repeated with different parameters bound as values. See `bind!` below).
71-
72-
The `SQLite.Stmt` will automatically closed/shutdown when it goes out of scope (i.e. the end of the Julia session, end of a function call wherein it was created, etc.)
73-
74-
* `SQLite.bind!(stmt::SQLite.Stmt,index,value)`
75-
76-
Used to bind values to parameter placeholders in an prepared `SQLite.Stmt`. From the SQLite documentation:
77-
78-
> Usually, though, it is not useful to evaluate exactly the same SQL statement more than once. More often, one wants to evaluate similar statements. For example, you might want to evaluate an INSERT statement multiple times though with different values to insert. To accommodate this kind of flexibility, SQLite allows SQL statements to contain parameters which are "bound" to values prior to being evaluated. These values can later be changed and the same prepared statement can be evaluated a second time using the new values.
79-
80-
> In SQLite, wherever it is valid to include a string literal, one can use a parameter in one of the following forms:
81-
82-
> ?
83-
> ?NNN
84-
> :AAA
85-
> $AAA
86-
> @AAA
87-
88-
> In the examples above, NNN is an integer value and AAA is an identifier. A parameter initially has a value of NULL. Prior to calling sqlite3_step() for the first time or immediately after sqlite3_reset(), the application can invoke one of the sqlite3_bind() interfaces to attach values to the parameters. Each call to sqlite3_bind() overrides prior bindings on the same parameter.
89-
90-
* `SQLite.execute!(stmt::SQLite.Stmt)`
91-
`SQLite.execute!(db::SQLite.DB, sql::String)`
92-
93-
Used to execute a prepared `SQLite.Stmt`. The 2nd method is a convenience method to pass in an SQL statement as a string which gets prepared and executed in one call. This method does not check for or return any results, hence it is only useful for database manipulation methods (i.e. ALTER, CREATE, UPDATE, DROP). To return results, see `SQLite.query` below.
94-
95-
* `SQLite.query(db::SQLite.DB, sql::String, values=[])`
96-
97-
An SQL statement `sql` is prepared, executed in the context of `db`, and results, if any, are returned. The return value is a `Data.Table` by default from the `DataStreams.jl` package. The `Data.Table` has a field `.data` which is a `Vector{NullableVector}` which holds the columns of data returned from the `sql` statement.
98-
99-
The values in `values` are used in parameter binding (see `bind!` above). If your statement uses nameless parameters `values` must be a `Vector` of the values you wish to bind to your statment. If your statement uses named parameters `values` must be a Dict where the keys are of type `Symbol`. The key must match an identifier name in the statement (the name **should not** include the ':', '@' or '$' prefix).
100-
101-
* `SQLite.drop!(db::SQLite.DB,table::String;ifexists::Bool=false)`
102-
`SQLite.dropindex!(db::SQLite.DB,index::String;ifexists::Bool=false)`
103-
104-
These are pretty self-explanatory. They're really just a convenience methods to execute DROP TABLE/DROP INDEX commands, while also calling "VACUUM" to clean out freed memory from the database.
105-
106-
* `SQLite.createindex!(db::DB,table::AbstractString,index::AbstractString,cols::AbstractString;unique::Bool=true,ifnotexists::Bool=false)`
107-
108-
Create a new index named `index` for `table` with the columns in `cols`, which should be a comma delimited list of column names. `unique` indicates whether the index will have unique values or not. `ifnotexists` will not throw an error if the index already exists.
109-
110-
* `SQLite.removeduplicates!(db,table::AbstractString,cols::AbstractString)`
111-
112-
A convenience method for the common task of removing duplicate rows in a dataset according to some subset of columns that make up a "primary key".
113-
114-
* `SQLite.tables(db::SQLite.DB)`
115-
116-
List the tables in an SQLite database `db`
117-
118-
* `SQLite.columns(db::SQLite.DB,table::AbstractString)`
119-
120-
List the columns in an SQLite table
121-
122-
* `SQLite.indices(db::SQLite.DB)`
123-
124-
List the indices that have been created in `db`
125-
126-
* `SQLite.Source(db::DB, sql; rows=0, stricttypes::Bool=true)`
127-
128-
Create an `SQLite.Source` type in `db` with the SQL statement `sql`. This prepares and executes the statement, but does not return any data. The source is ready to be streamed to any sink type with an appropriate `Data.stream!` method defined. `rows` can be used to fetch a specific number of rows if known before hand and can help in pre-allocating for sinks. `stricttypes=false` can be used to relax type requirements on returned columns; typically, each value in a column must be of the same type, but SQLite itself uses a fairly weak typing scheme which allows any value to be in a column, regardless of type. Working with data in Julia is much more useful in strongly-typed structures, so by default we try to return strongly-typed columns, but this can be relaxed.
129-
130-
* `SQLite.Source(sink::SQLite.Sink,sql)`
131-
132-
Creates an `SQLite.Source` type according the `sql` command executed in the same `db` as `sink`. By default, the `sql` command is `select * from $(sink.tablename)`.
133-
134-
* `Data.stream!(source::SQLite.Source,::Type{Data.Table})`
135-
136-
Create a `Data.Table` and stream the data from an `SQLite.Source` into it.
137-
138-
* `Data.stream!(source::SQLite.Source,sink::CSV.Sink;header::Bool=true)`
139-
140-
stream the data from `source` to a `CSV.Sink`. `header` indicates whether the column names will be written first to `sink`.
141-
142-
* `SQLite.Sink(schema::Data.Schema,db::DB,tablename;temp::Bool=false,ifnotexists::Bool=true)`
143-
144-
Create a new SQLite table as a sink to stream data to in `db`. `schema` is used to create the column names and types. If no `tablename` is supplied, one will be generated. `temp` indicates whether the table will be temporary, i.e. if it will be automatically destroyed when the `db` is closed.
145-
146-
* `SQLite.Sink(source::Data.Source, db::DB, tablename)`
147-
148-
Create a new SQLite table as a sink in `db` according to the `Data.schema(source)`.
149-
150-
* `Data.stream!(dt::Data.Table,sink::SQLite.Sink)`
151-
152-
stream the data from a `Data.Table` to `sink`
153-
154-
* `Data.stream!(source::CSV.Source,sink::SQLite.Sink)`
155-
156-
stream the data from a `CSV.Source` to `sink`
157-
158-
* `SQLite.register(db::SQLite.DB, func::Function; nargs::Int=-1, name::AbstractString=string(func), isdeterm::Bool=true)`
159-
* `SQLite.register(db::SQLite.DB, init, step::Function, final::Function=identity; nargs::Int=-1, name::AbstractString=string(final), isdeterm::Bool=true)`
160-
161-
Register a scalar (first method) or aggregate (second method) function with a `SQLite.DB`.
162-
163-
* `@register db function`
164-
165-
Automatically define then register `function` with a `SQLite.DB`.
166-
167-
* `sr"..."`
168-
169-
This string literal is used to escape all special characters in the string, useful for using regex in a query.
170-
171-
* `SQLite.sqlreturn(contex, val)`
172-
173-
This function should never be called explicitly. Instead it is exported so that it can be overloaded when necessary, see below.
174-
175-
#### User Defined Functions
176-
177-
##### SQLite Regular Expressions
178-
179-
SQLite provides syntax for calling the [`regexp` function](http://sqlite.org/lang_expr.html#regexp) from inside `WHERE` clauses. Unfortunately, however, SQLite does not provide a default implementation of the `regexp` function so SQLite.jl creates one automatically when you open a database. The function can be called in the following ways (examples using the [Chinook Database](http://chinookdatabase.codeplex.com/))
180-
181-
```julia
182-
julia> using SQLite
183-
184-
julia> db = SQLite.DB("Chinook_Sqlite.sqlite")
185-
186-
julia> # using SQLite's in-built syntax
187-
188-
julia> SQLite.query(db, "SELECT FirstName, LastName FROM Employee WHERE LastName REGEXP 'e(?=a)'")
189-
1x2 ResultSet
190-
| Row | "FirstName" | "LastName" |
191-
|-----|-------------|------------|
192-
| 1 | "Jane" | "Peacock" |
193-
194-
julia> # explicitly calling the regexp() function
195-
196-
julia> SQLite.query(db, "SELECT * FROM Genre WHERE regexp('e[trs]', Name)")
197-
6x2 ResultSet
198-
| Row | "GenreId" | "Name" |
199-
|-----|-----------|----------------------|
200-
| 1 | 3 | "Metal" |
201-
| 2 | 4 | "Alternative & Punk" |
202-
| 3 | 6 | "Blues" |
203-
| 4 | 13 | "Heavy Metal" |
204-
| 5 | 23 | "Alternative" |
205-
| 6 | 25 | "Opera" |
206-
207-
julia> # you can even do strange things like this if you really want
208-
209-
julia> SQLite.query(db, "SELECT * FROM Genre ORDER BY GenreId LIMIT 2")
210-
2x2 ResultSet
211-
| Row | "GenreId" | "Name" |
212-
|-----|-----------|--------|
213-
| 1 | 1 | "Rock" |
214-
| 2 | 2 | "Jazz" |
215-
216-
julia> SQLite.query(db, "INSERT INTO Genre VALUES (regexp('^word', 'this is a string'), 'My Genre')")
217-
1x1 ResultSet
218-
| Row | "Rows Affected" |
219-
|-----|-----------------|
220-
| 1 | 0 |
221-
222-
julia> SQLite.query(db, "SELECT * FROM Genre ORDER BY GenreId LIMIT 2")
223-
2x2 ResultSet
224-
| Row | "GenreId" | "Name" |
225-
|-----|-----------|------------|
226-
| 1 | 0 | "My Genre" |
227-
| 2 | 1 | "Rock" |
228-
```
229-
230-
Due to the heavy use of escape characters you may run into problems where julia parses out some backslashes in your query, for example `"\y"` simply becomes `"y"`. For example the following two queries are identical
231-
232-
```julia
233-
julia> SQLite.query(db, "SELECT * FROM MediaType WHERE Name REGEXP '-\d'")
234-
1x1 ResultSet
235-
| Row | "Rows Affected" |
236-
|-----|-----------------|
237-
| 1 | 0 |
238-
239-
julia> SQLite.query(db, "SELECT * FROM MediaType WHERE Name REGEXP '-d'")
240-
1x1 ResultSet
241-
| Row | "Rows Affected" |
242-
|-----|-----------------|
243-
| 1 | 0 |
244-
```
245-
246-
This can be avoided in two ways. You can either escape each backslash yourself or you can use the sr"..." string literal that SQLite.jl exports. The previous query can then successfully be run like so
247-
248-
```julia
249-
julia> # manually escaping backslashes
250-
251-
julia> SQLite.query(db, "SELECT * FROM MediaType WHERE Name REGEXP '-\\d'")
252-
1x2 ResultSet
253-
| Row | "MediaTypeId" | "Name" |
254-
|-----|---------------|-------------------------------|
255-
| 1 | 3 | "Protected MPEG-4 video file" |
256-
257-
julia> # using sr"..."
258-
259-
julia> SQLite.query(db, sr"SELECT * FROM MediaType WHERE Name REGEXP '-\d'")
260-
1x2 ResultSet
261-
| Row | "MediaTypeId" | "Name" |
262-
|-----|---------------|-------------------------------|
263-
| 1 | 3 | "Protected MPEG-4 video file" |
264-
```
265-
266-
The sr"..." currently escapes all special characters in a string but it may be changed in the future to escape only characters which are part of a regex.
267-
268-
##### Custom Scalar Functions
269-
270-
SQLite.jl also provides a way that you can implement your own [Scalar Functions](https://www.sqlite.org/lang_corefunc.html). This is done using the `register` function and macro.
271-
272-
`@register` takes a `SQLite.DB` and a function. The function can be in block syntax
273-
274-
```julia
275-
julia> @register db function add3(x)
276-
x + 3
277-
end
278-
```
279-
280-
inline function syntax
281-
282-
```julia
283-
julia> @register db mult3(x) = 3 * x
284-
```
285-
286-
and previously defined functions
287-
288-
```julia
289-
julia> @register db sin
290-
```
291-
292-
The `SQLite.register` function takes optional arguments; `nargs` which defaults to `-1`, `name` which defaults to the name of the function, `isdeterm` which defaults to `true`. In practice these rarely need to be used.
293-
294-
The `SQLite.register` function uses the `sqlreturn` function to return your function's return value to SQLite. By default, `sqlreturn` maps the returned value to a [native SQLite type](http://sqlite.org/c3ref/result_blob.html) or, failing that, serializes the julia value and stores it as a `BLOB`. To change this behaviour simply define a new method for `sqlreturn` which then calls a previously defined method for `sqlreturn`. Methods which map to native SQLite types are
295-
296-
```julia
297-
sqlreturn(context, ::NullType)
298-
sqlreturn(context, val::Int32)
299-
sqlreturn(context, val::Int64)
300-
sqlreturn(context, val::Float64)
301-
sqlreturn(context, val::UTF16String)
302-
sqlreturn(context, val::String)
303-
sqlreturn(context, val::Any)
304-
```
305-
306-
As an example, say you would like `BigInt`s to be stored as `TEXT` rather than a `BLOB`. You would simply need to define the following method
307-
308-
```julia
309-
sqlreturn(context, val::BigInt) = sqlreturn(context, string(val))
310-
```
311-
312-
Another example is the `sqlreturn` used by the `regexp` function. For `regexp` to work correctly it must return it must return an `Int` (more specifically a `0` or `1`) but `ismatch` (used by `regexp`) returns a `Bool`. For this reason the following method was defined
313-
314-
```julia
315-
sqlreturn(context, val::Bool) = sqlreturn(context, int(val))
316-
```
317-
318-
Any new method defined for `sqlreturn` must take two arguments and must pass the first argument straight through as the first argument.
319-
320-
#### Custom Aggregate Functions
321-
322-
Using the `SQLite.register` function, you can also define your own aggregate functions with largely the same semantics.
323-
324-
The `SQLite.register` function for aggregates must take a `SQLite.DB`, an initial value, a step function and a final function. The first argument to the step function will be the return value of the previous function (or the initial value if it is the first iteration). The final function must take a single argument which will be the return value of the last step function.
325-
326-
```julia
327-
julia> dsum(prev, cur) = prev + cur
328-
329-
julia> dsum(prev) = 2 * prev
330-
331-
julia> SQLite.register(db, 0, dsum, dsum)
332-
```
333-
334-
If no name is given the name of the first (step) function is used (in this case "dsum"). You can also use lambdas, the following does the same as the previous code snippet
335-
336-
```julia
337-
julia> SQLite.register(db, 0, (p,c) -> p+c, p -> 2p, name="dsum")
338-
```

docs/make.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,6 @@ deploydocs(
1212
target = "build",
1313
deps = nothing,
1414
make = nothing,
15-
julia = "0.5",
15+
julia = "1.0",
1616
osname = "linux"
1717
)

docs/src/index.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ Will bind `values` to any parameters in `sql`.
6262
`stricttypes=false` will remove strict column typing in the result set, making each column effectively `Vector{Any}`; in sqlite, individual
6363
column values are only loosely associated with declared column types, and instead each carry their own type information. This can lead to
6464
type errors when trying to query columns when a single type is expected.
65-
`nullable` controls whether `null` (`missing` in Julia) values are expected in a column.
65+
`nullable` controls whether `NULL` (`missing` in Julia) values are expected in a column.
6666

6767
An `SQLite.Query` object will iterate NamedTuple rows by default, and also supports the Tables.jl interface for integrating with
6868
any other Tables.jl implementation. Due note however that iterating an sqlite result set is a forward-once-only operation. If you need

src/tables.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@ Will bind `values` to any parameters in `sql`.
7171
`stricttypes=false` will remove strict column typing in the result set, making each column effectively `Vector{Any}`; in sqlite, individual
7272
column values are only loosely associated with declared column types, and instead each carry their own type information. This can lead to
7373
type errors when trying to query columns when a single type is expected.
74-
`nullable` controls whether `null` (`missing` in Julia) values are expected in a column.
74+
`nullable` controls whether `NULL` (`missing` in Julia) values are expected in a column.
7575
7676
An `SQLite.Query` object will iterate NamedTuple rows by default, and also supports the Tables.jl interface for integrating with
7777
any other Tables.jl implementation. Due note however that iterating an sqlite result set is a forward-once-only operation. If you need

0 commit comments

Comments
 (0)