Dont index style nodes.
[beagle.git] / beagled / Mono.Data.SqliteClient / SqliteConnection.cs
blob98812e67bc0670b8cc0be25eb242f7b58b165ffa
1 //
2 // Mono.Data.SqliteClient.SqliteConnection.cs
3 //
4 // Represents an open connection to a Sqlite database file.
5 //
6 // Author(s): Vladimir Vukicevic <vladimir@pobox.com>
7 // Everaldo Canuto <everaldo_canuto@yahoo.com.br>
8 //
9 // Copyright (C) 2002 Vladimir Vukicevic
11 // Permission is hereby granted, free of charge, to any person obtaining
12 // a copy of this software and associated documentation files (the
13 // "Software"), to deal in the Software without restriction, including
14 // without limitation the rights to use, copy, modify, merge, publish,
15 // distribute, sublicense, and/or sell copies of the Software, and to
16 // permit persons to whom the Software is furnished to do so, subject to
17 // the following conditions:
18 //
19 // The above copyright notice and this permission notice shall be
20 // included in all copies or substantial portions of the Software.
21 //
22 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
23 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
24 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
25 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
26 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
27 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
28 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
31 using System;
32 using System.Runtime.InteropServices;
33 using System.Data;
34 using System.Text;
36 namespace Mono.Data.SqliteClient
38 public class SqliteConnection : IDbConnection
41 #region Fields
43 private string conn_str;
44 private string db_file;
45 private int db_mode;
46 private int db_version;
47 private IntPtr sqlite_handle;
48 private ConnectionState state;
49 private Encoding encoding;
51 #endregion
53 #region Constructors and destructors
55 public SqliteConnection ()
57 db_file = null;
58 db_mode = 0644;
59 db_version = 2;
60 state = ConnectionState.Closed;
61 sqlite_handle = IntPtr.Zero;
62 encoding = null;
65 public SqliteConnection (string connstring) : this ()
67 ConnectionString = connstring;
70 public void Dispose ()
72 Close ();
75 #endregion
77 #region Properties
79 public string ConnectionString {
80 get { return conn_str; }
81 set { SetConnectionString(value); }
84 public int ConnectionTimeout {
85 get { return 0; }
88 public string Database {
89 get { return db_file; }
92 public ConnectionState State {
93 get { return state; }
96 public Encoding Encoding {
97 get { return encoding; }
100 internal int Version {
101 get { return db_version; }
104 internal IntPtr Handle {
105 get { return sqlite_handle; }
108 public int LastInsertRowId {
109 get {
110 if (Version == 3)
111 return Sqlite.sqlite3_last_insert_rowid (Handle);
112 else
113 return Sqlite.sqlite_last_insert_rowid (Handle);
117 #endregion
119 #region Private Methods
121 private void SetConnectionString(string connstring)
123 if (connstring == null) {
124 Close ();
125 conn_str = null;
126 return;
129 if (connstring != conn_str) {
130 Close ();
131 conn_str = connstring;
133 db_file = null;
134 db_mode = 0644;
136 string[] conn_pieces = connstring.Split (',');
137 for (int i = 0; i < conn_pieces.Length; i++) {
138 string piece = conn_pieces [i].Trim ();
139 if (piece.Length == 0) { // ignore empty elements
140 continue;
142 string[] arg_pieces = piece.Split ('=');
143 if (arg_pieces.Length != 2) {
144 throw new InvalidOperationException ("Invalid connection string");
146 string token = arg_pieces[0].ToLower (System.Globalization.CultureInfo.InvariantCulture).Trim ();
147 string tvalue = arg_pieces[1].Trim ();
148 string tvalue_lc = arg_pieces[1].ToLower (System.Globalization.CultureInfo.InvariantCulture).Trim ();
149 if (token == "uri") {
150 if (tvalue_lc.StartsWith ("file://")) {
151 db_file = tvalue.Substring (7);
152 } else if (tvalue_lc.StartsWith ("file:")) {
153 db_file = tvalue.Substring (5);
154 } else if (tvalue_lc.StartsWith ("/")) {
155 db_file = tvalue;
156 } else {
157 throw new InvalidOperationException ("Invalid connection string: invalid URI");
159 } else if (token == "mode") {
160 db_mode = Convert.ToInt32 (tvalue);
161 } else if (token == "version") {
162 db_version = Convert.ToInt32 (tvalue);
163 } else if (token == "encoding") { // only for sqlite2
164 encoding = Encoding.GetEncoding (tvalue);
168 if (db_file == null) {
169 throw new InvalidOperationException ("Invalid connection string: no URI");
174 #endregion
176 #region Internal Methods
178 internal void StartExec ()
180 // use a mutex here
181 state = ConnectionState.Executing;
184 internal void EndExec ()
186 state = ConnectionState.Open;
189 #endregion
191 #region Public Methods
193 public IDbTransaction BeginTransaction ()
195 if (state != ConnectionState.Open)
196 throw new InvalidOperationException("Invalid operation: The connection is closed");
198 SqliteTransaction t = new SqliteTransaction();
199 t.Connection = this;
200 SqliteCommand cmd = this.CreateCommand();
201 cmd.CommandText = "BEGIN";
202 cmd.ExecuteNonQuery();
203 return t;
206 public IDbTransaction BeginTransaction (IsolationLevel il)
208 throw new InvalidOperationException();
211 public void Close ()
213 if (state != ConnectionState.Open) {
214 return;
217 state = ConnectionState.Closed;
219 if (Version == 3)
220 Sqlite.sqlite3_close (sqlite_handle);
221 else
222 Sqlite.sqlite_close(sqlite_handle);
223 sqlite_handle = IntPtr.Zero;
226 public void ChangeDatabase (string databaseName)
228 throw new NotImplementedException ();
231 IDbCommand IDbConnection.CreateCommand ()
233 return CreateCommand ();
236 public SqliteCommand CreateCommand ()
238 return new SqliteCommand (null, this);
241 public void Open ()
243 if (conn_str == null) {
244 throw new InvalidOperationException ("No database specified");
247 if (state != ConnectionState.Closed) {
248 return;
251 IntPtr errmsg = IntPtr.Zero;
253 if (Version == 2){
254 try {
255 sqlite_handle = Sqlite.sqlite_open(db_file, db_mode, out errmsg);
256 if (errmsg != IntPtr.Zero) {
257 string msg = Marshal.PtrToStringAnsi (errmsg);
258 Sqlite.sqliteFree (errmsg);
259 throw new ApplicationException (msg);
261 } catch (DllNotFoundException dll) {
262 db_version = 3;
265 if (Version == 3) {
266 int err = Sqlite.sqlite3_open16(db_file, out sqlite_handle);
267 if (err == (int)SqliteError.ERROR)
268 throw new ApplicationException (Marshal.PtrToStringUni( Sqlite.sqlite3_errmsg16 (sqlite_handle)));
269 } else {
271 state = ConnectionState.Open;
274 #endregion