別のクラスで読み取ることができるように、リーダーを返そうとしています。そして、これを呼び出すとき: return cmd.ExecuteReader(); Mono.Data.Sqlite.SqliteException が発生します: たとえば、挿入クエリを呼び出して cmd.ExecuteNonQuery(); を呼び出そうとすると、同じことが起こります。私は次のクラスを持っています:
データベース.cs:
public class Database
{
private SqliteConnection connection;
public string connectiondata;
private static string _LocalDatabasePath = Path.Combine(System.Environment.GetFolderPath(System.Environment.SpecialFolder.Personal), "LocalData.db3");
public Database(string ConnectionString)
{
this.connection = new SqliteConnection(ConnectionString);
}
public Database(SqliteConnection Connection)
{
this.connection = Connection;
}
public static UsersDatabase User { get { return new UsersDatabase("Data Source=" + _LocalDatabasePath); } }
#region Queries
protected SqliteDataReader SelectQuery(string columns, string table, string condition)
{
if (this.Connected)
{
SqliteCommand cmd = this.connection.CreateCommand();
cmd.CommandText = "SELECT " + columns + " FROM " + table + (string.IsNullOrEmpty(condition) ? "" : " WHERE " + condition);
cmd.CommandType = CommandType.Text;
return cmd.ExecuteReader();
}
else
{
throw new Exception("Inte ansluten till databasen");
}
}
protected SqliteDataReader SelectQuery(string columns, string table)
{
return this.SelectQuery(columns, table, "");
}
protected void InsertQuery(string table, string columns, string values)
{
if (this.Connected)
{
SqliteCommand cmd = this.connection.CreateCommand();
cmd.CommandText = "INSERT INTO " + table + "(" + columns + ") VALUES(" + values + ")";
cmd.ExecuteNonQuery();
}
else
{
throw new Exception("Inte ansluten till databasen");
}
}
#endregion
#region Connection
public bool Connected
{
get
{
if (this.connection == null)
{
return false;
}
if (this.connection.State == ConnectionState.Open)
{
return true;
}
return false;
}
}
public void Connect()
{
if (!this.Connected)
{
string db = _LocalDatabasePath;
bool exists = File.Exists(db);
if (!exists)
{
SqliteConnection.CreateFile(db);
}
this.connection = new SqliteConnection("Data Source=" + db);
this.connection.Open();
}
}
public void Close()
{
if (this.Connected)
{
this.connection.Close();
}
}
#endregion
}
}
ユーザーデータベース.cs:
public class UsersDatabase : Database
{
public UsersDatabase(string connectionstring)
: base(connectionstring)
{
}
public UsersDatabase(SqliteConnection connection)
: base(connection)
{
}
public void CreateUser()
{
this.Connect();
this.InsertQuery("People", "PersonID, FirstName, LastName", "'" + "namn11" + "', '" + "enamn11" + "'");
this.Close();
}
public UserStruct[] GetAllUsers()
{
List<UserStruct> templist = new List<UserStruct>();
this.Connect();
SqliteDataReader reader = this.SelectQuery("*", "People", "");
while (reader.Read())
{
UserStruct tmpuser = new UserStruct();
tmpuser.ID = reader["PersonID"].ToString();
tmpuser.Name = reader["FirstName"].ToString();
tmpuser.LastName = reader["LastName"].ToString();
templist.Add(tmpuser);
}
this.Close();
return templist.ToArray();
}
}
Activity1.cs:
[Activity(Label = "example_proj", MainLauncher = true, Icon = "@drawable/icon")]
public class Activity1 : Activity
{
protected override void OnCreate(Bundle bundle)
{
base.OnCreate(bundle);
// Set our view from the "main" layout resource
SetContentView(Resource.Layout.Main);
Button btn2 = FindViewById<Button>(Resource.Id.btn2);
btn2.Click += new EventHandler(btn2_Click);
}
void btn2_Click(object sender, EventArgs e)
{
UserStruct[] tmpusr = UsersDatabase.User.GetAllUsers();//get usrs
}
}
だから... アクティビティから、UsersDatabase GetAllUsers() または CreateUser() を呼び出します。UsersDatabase は、Database クラスを使用してクエリと接続を支援します。したがって、UsersDatabase から最初に Connect() メソッドを呼び出して DB への接続を確立し、次にたとえば SelectQuery() を呼び出してリーダーを返します。このリーダーは後で UsersDatabase クラスで読み取り、構造体に情報を入力します。 activity1 に戻ります。
私が言ったように、例外が発生したときにリーダーを返すところまで行きます。接続が開いており、DB が存在します。