In (early) praise of SQLite and EF4

2011-05-28 Thread Greg Keogh
Folks, just in case anyone was wondering ... my experiments so far indicate
that SQLite works nicely with Entity Framework 4. I expected horrors, but I
guess the authors of the SQLite ADO provider have obeyed the rules. A couple
of little irritations have surfaced.

 

The INTEGER type in SQLite which is used for primary keys is an Int64
whereas under SQL Server and SQL CE it was an Int32. I had to adjust my code
to prevent cast errors on ExecScalar calls.

 

Bulk inserts of a thousand rows or so into SQLite tables seems
excruciatingly slow. Perhaps there is some bulk insert trick or transaction
gotcha affecting this that I'm not aware of yet.

 

I have UNIQUEIDENTIFIER columns in the SQL Server tables I'm migrating to
SQLite, but my reading so far is confusing about what underlying string
value is expected to be stored by the caller in such a column in SQLite. I
guess it's any string value which can be TypeConveter'd to and from a GUID.
That's fine, but I can't find a NEWID() equivalent and some people seem to
have invented their own ones by a messy combination of functions. I gave up
and used a BIGINT SQLite column instead and filled with DEFAULT
(ABS(RANDOM()). This seems like a good replacement for a GUID.

 

I'm still unsure about the corresponding CLR type widths for INT, INTEGER,
BIGINT, etc. More reading will sort this out I guess.

 

I haven't pushed EF4 really hard yet other than proving it works, but it
looks promising for more intense work. This is great, as I'm planning to
re-jig one of my apps so that it uses SQLite and has absolutely no install
footprint like it used to have with SQL CE.

 

Greg



Re: SQLite bulk insert performance

2011-05-28 Thread Joseph Cooney
I wouldn't bother e-mailing the SQLite folks. This is by design, and is a
well known behaviour with SQLite. From memory if you don't explicitly have a
transaction then one gets created for each operation, which slows things
down.

Joseph

On Sun, May 29, 2011 at 10:27 AM, Greg Keogh g...@mira.net wrote:

 Here’s a serious heads-up for you:



 Last night I was bulk migrating about 20 rows from my old SQL Express
 database into my new SQLite one. I wondered why it took about 10 minutes to
 insert 1000 rows into one table, and when it got to the 6 row table I
 was curious about how long that would take. So I left the machine running
 while we met friends for dinner at a Turkish restaurant. Four hours later
 it’s still running the same step. I noticed that a journal file was
 flickering madly in Windows Explorer, so I guessed it was some transactional
 problem.



 My code is plain ADO.NET like this:



 using (SQLiteCommand ...)

 {

 using (SQLiteCommand ...)

 {

 for (...)

 {

 ExecNonQuery(... INSERT ...)

 }

 }

 }



 This morning a few web searches hinted that I had to use PRAGMA
 synchronous = OFF. That’s too weird, so I put a using DbTransaction around
 the bulk inserts and now the whole migrations runs in 10 seconds.



 I’m going to cc a copy of this post to the authors of SQLite, as this is a
 shocking gotcha. I’m utterly gobsmacked by the poor performance of the
 inserts without a transaction around them.



 Greg




-- 

w: http://jcooney.net
t: @josephcooney


Re: SQLite bulk insert performance

2011-05-28 Thread Mark Hurd
Isn't that exactly the same as the default mode for SQL Server?

On 29 May 2011 12:52, Joseph Cooney joseph.coo...@gmail.com wrote:
 I wouldn't bother e-mailing the SQLite folks. This is by design, and is a
 well known behaviour with SQLite. From memory if you don't explicitly have a
 transaction then one gets created for each operation, which slows things
 down.

 Joseph
 On Sun, May 29, 2011 at 10:27 AM, Greg Keogh g...@mira.net wrote:

 Here’s a serious heads-up for you:

 Last night I was bulk migrating about 20 rows from my old SQL Express
 database into my new SQLite one. I wondered why it took about 10 minutes to
 insert 1000 rows into one table, and when it got to the 6 row table I
 was curious about how long that would take. So I left the machine running
 while we met friends for dinner at a Turkish restaurant. Four hours later
 it’s still running the same step. I noticed that a journal file was
 flickering madly in Windows Explorer, so I guessed it was some transactional
 problem.

 My code is plain ADO.NET like this:

 using (SQLiteCommand ...)
 {
     using (SQLiteCommand ...)
     {

     for (...)
     {

     ExecNonQuery(... INSERT ...)

     }
     }
 }


 This morning a few web searches hinted that I had to use PRAGMA
 synchronous = OFF. That’s too weird, so I put a using DbTransaction around
 the bulk inserts and now the whole migrations runs in 10 seconds.

 I’m going to cc a copy of this post to the authors of SQLite, as this is a
 shocking gotcha. I’m utterly gobsmacked by the poor performance of the
 inserts without a transaction around them.


 Greg

 --

 w: http://jcooney.net
 t: @josephcooney
-- 
Regards,
Mark Hurd, B.Sc.(Ma.)(Hons.)


Re: SQLite bulk insert performance

2011-05-28 Thread Joseph Cooney
True, but I think the cost associated with creating a transaction is
different with SQLite. I think SQLite needs to opening, writing to, and
closing the journal file each time it creates a transaction which is
apparently expensive. Maybe since SQL Server is a service it keeps keeps the
journal file open.

Joseph

On Sun, May 29, 2011 at 1:29 PM, Mark Hurd markeh...@gmail.com wrote:

 Isn't that exactly the same as the default mode for SQL Server?

 On 29 May 2011 12:52, Joseph Cooney joseph.coo...@gmail.com wrote:
  I wouldn't bother e-mailing the SQLite folks. This is by design, and is a
  well known behaviour with SQLite. From memory if you don't explicitly
 have a
  transaction then one gets created for each operation, which slows things
  down.
 
  Joseph
  On Sun, May 29, 2011 at 10:27 AM, Greg Keogh g...@mira.net wrote:
 
  Here’s a serious heads-up for you:
 
  Last night I was bulk migrating about 20 rows from my old SQL
 Express
  database into my new SQLite one. I wondered why it took about 10 minutes
 to
  insert 1000 rows into one table, and when it got to the 6 row table
 I
  was curious about how long that would take. So I left the machine
 running
  while we met friends for dinner at a Turkish restaurant. Four hours
 later
  it’s still running the same step. I noticed that a journal file was
  flickering madly in Windows Explorer, so I guessed it was some
 transactional
  problem.
 
  My code is plain ADO.NET like this:
 
  using (SQLiteCommand ...)
  {
  using (SQLiteCommand ...)
  {
 
  for (...)
  {
 
  ExecNonQuery(... INSERT ...)
 
  }
  }
  }
 
 
  This morning a few web searches hinted that I had to use PRAGMA
  synchronous = OFF. That’s too weird, so I put a using DbTransaction
 around
  the bulk inserts and now the whole migrations runs in 10 seconds.
 
  I’m going to cc a copy of this post to the authors of SQLite, as this is
 a
  shocking gotcha. I’m utterly gobsmacked by the poor performance of the
  inserts without a transaction around them.
 
 
  Greg
 
  --
 
  w: http://jcooney.net
  t: @josephcooney
 --
 Regards,
 Mark Hurd, B.Sc.(Ma.)(Hons.)




-- 

w: http://jcooney.net
t: @josephcooney