Skip to content

Commit 83d30d9

Browse files
authored
Adding last query executed to table query. (#18)
1 parent 9d2cea0 commit 83d30d9

File tree

4 files changed

+53
-0
lines changed

4 files changed

+53
-0
lines changed

SQLite.Net.Tests/StringQueryTest.cs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -63,5 +63,15 @@ public void StartsWith()
6363
List<Product> bs = db.Table<Product>().Where(x => x.Name.StartsWith("B")).ToList();
6464
Assert.AreEqual(1, bs.Count);
6565
}
66+
67+
[Test]
68+
public void RegexTest()
69+
{
70+
var fs = db.Table<Product>().Where(x => x.Name.IsMatch("^F.*")).ToList();
71+
Assert.AreEqual(2, fs.Count);
72+
73+
var bs = db.Table<Product>().Where(x => x.Name.IsMatch(".*o$")).ToList();
74+
Assert.AreEqual(1, bs.Count);
75+
}
6676
}
6777
}

src/SQLite.Net/Interop/SQLiteApi.cs

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
using System;
2+
using System.Text.RegularExpressions;
23
using SQLitePCL;
34

45
namespace SQLite.Net2
@@ -14,6 +15,23 @@ public Result Open(string filename, out IDbHandle db, int flags, string zvfs)
1415
return (Result)r;
1516
}
1617

18+
public int BindRegexpFunction(IDbHandle db)
19+
{
20+
void RegexMatch(
21+
sqlite3_context ctx,
22+
object user_data,
23+
sqlite3_value[] args)
24+
{
25+
var pattern = raw.sqlite3_value_text(args[0]).utf8_to_string();
26+
var input = raw.sqlite3_value_text(args[1]).utf8_to_string();
27+
var r = Regex.IsMatch(input, pattern);
28+
raw.sqlite3_result_int(ctx, r ? 1 : 0);
29+
}
30+
31+
var handle = (DbHandle)db;
32+
return raw.sqlite3_create_function(handle.DbPtr, "REGEXP", 2, null, RegexMatch);
33+
}
34+
1735
public ExtendedResult ExtendedErrCode(IDbHandle db)
1836
{
1937
var internalDbHandle = (DbHandle)db;

src/SQLite.Net/SQLiteConnection.cs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -145,6 +145,8 @@ public SQLiteConnection(string databasePath, SQLiteOpenFlags openFlags = SQLiteO
145145
if (r != Result.OK)
146146
throw new SQLiteException(r, $"Could not open database file: {DatabasePath} ({r})");
147147

148+
sqlite.BindRegexpFunction(handle);
149+
148150
Handle = handle ?? throw new NullReferenceException("Database handle is null");
149151
_open = true;
150152
databaseOpenFlags = openFlags;

src/SQLite.Net/TableQuery.cs

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@
2929
using System.Reflection;
3030
using System.Runtime.CompilerServices;
3131
using System.Text;
32+
using System.Text.RegularExpressions;
3233

3334
namespace SQLite.Net2
3435
{
@@ -44,6 +45,7 @@ public class TableQuery<T> : BaseTableQuery, IEnumerable<T>
4445
private int? _offset;
4546
private List<Ordering> _orderBys;
4647
private Expression _where;
48+
private string? _lastQueryExecuted;
4749

4850
private TableQuery(SQLiteConnection conn, TableMapping table)
4951
{
@@ -64,6 +66,7 @@ public TableQuery(SQLiteConnection conn)
6466

6567
public TableMapping Table { get; private set; }
6668

69+
public string? LastQueryExecuted => _lastQueryExecuted;
6770

6871
public IEnumerator<T> GetEnumerator()
6972
{
@@ -161,6 +164,7 @@ public int Delete( Expression<Func<T, bool>> predExpr)
161164
cmdText += " where " + w.CommandText;
162165
var command = Connection.CreateCommand(cmdText, args.ToArray());
163166

167+
_lastQueryExecuted = cmdText;
164168
var result = command.ExecuteNonQuery();
165169
return result;
166170
}
@@ -355,6 +359,8 @@ private SQLiteCommand GenerateCommand( string selectionList)
355359
}
356360
cmdText.Append(" offset ").Append(_offset.Value);
357361
}
362+
363+
_lastQueryExecuted = cmdText.ToString();
358364
return Connection.CreateCommand(cmdText.ToString(), args.ToArray());
359365
}
360366

@@ -536,6 +542,10 @@ private CompileResult CompileExpr( Expression expr, List<object> queryArgs)
536542
{
537543
sqlCall.AppendFormat("(replace({0}, {1}, {2}))", obj.CommandText, args[0].CommandText, args[1].CommandText);
538544
}
545+
else if (call.Method.Name == nameof(TableQueryExtensions.IsMatch) && args.Length == 2)
546+
{
547+
sqlCall.AppendFormat("{0} REGEXP {1}", args[0].CommandText, args[1].CommandText);
548+
}
539549
else
540550
{
541551
sqlCall.Append(call.Method.Name.ToLower()).Append("(").Append(String.Join(",", args.Select(a => a.CommandText).ToArray())).Append(")");
@@ -825,4 +835,17 @@ private class CompileResult
825835
public object Value { get; set; }
826836
}
827837
}
838+
839+
public static class TableQueryExtensions
840+
{
841+
public static bool IsMatch(this ISerializable<string> a, string b)
842+
{
843+
return IsMatch(a.Serialize(), b);
844+
}
845+
846+
public static bool IsMatch(this string a, string b)
847+
{
848+
return Regex.IsMatch(a, b);
849+
}
850+
}
828851
}

0 commit comments

Comments
 (0)