The goal of the Adapdev.Data.Sql namespace is to allow for the generation of database specific SQL through a database independent API.
The SQL API has three main pieces
A query object. This can be one of the following:
ISelectQuery
IInsertQuery
IDeleteQuery
IUpdateQuery
An ICriteria object. This provides all sql starting from "WHERE..."
A QueryFactory object. This is reponsible for returning the correct query object.
Here is a simple example without any criteria:
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.ORACLE);
query.SetTable("sometable");
query.AddAll();
Console.WriteLine(query.Statement);
// Output: SELECT * FROM sometable;
Here's the same example, but with criteria included:
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.ORACLE);
query.SetTable("sometable");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddEqualTo("somecolumn", 1);
query.SetCriteria(criteria);
Console.WriteLine(query.Statement);
// Output: SELECT * FROM sometable WHERE somecolumn = 1;The generated code will "mutate" based on the target database. Let's revisit the example, but use a DateTime as the value, since the syntax for this varies from database to database.
public string GetSelectStatement(DbType dbType)
{
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.ORACLE);
query.SetTable("sometable");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddEqualTo("somecolumn", DateTime.Now);
query.SetCriteria(criteria);
return query.Statement;
}
... // somewhere else in your code
Console.WriteLine(GetSelectStatement(DbType.ACCESS));
// Output:
SELECT * FROM [sometable] WHERE [somecolumn] = #1/30/2005 1:21:05 PM#;
Console.WriteLine(GetSelectStatement(DbType.ORACLE));
// Output:
SELECT * FROM sometable WHERE somecolumn = '1/30/2005 1:21:05 PM';
As you can see, the syntax around the column and table names changed, as did the delimiters for the passed in date time value.
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.AddAll();
// Example Output:
SELECT * FROM [sometable];
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.Add("somecolumn");
query.Add("somecolumn2");
// Example Output:
SELECT [somecolumn], [somecolumn2] FROM [sometable];
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.Add("somecolumn");
query.Add("table2","somecolumn2");
// Example Output:
SELECT [somecolumn], [table2].[somecolumn2] FROM [sometable];
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.Add("column1");
query.AddColumnAlias("table2", "column2", "alias2");
query.AddColumnAlias("column3", "alias3");
// Example Output:
SELECT [column1], [table2].[column2] AS alias2,
[column3] AS alias3 FROM [sometable];
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.AddCount("column");
// Example Output:
SELECT COUNT([column]) FROM [sometable];
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.AddCountAll();
// Example Output:
SELECT COUNT(*) FROM [sometable];
By default, ORDER BY is ASC
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.AddAll();
query.AddOrderBy("column1");
query.AddOrderBy("column2");
// Example Output:
SELECT * FROM [sometable] ORDER BY [column1], [column2] ASC;
You can override this by setting the OrderBy property
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.AddAll();
query.AddOrderBy("column1");
query.AddOrderBy("column2");
query.OrderBy = OrderBy.DESCENDING;
// Example Output:
SELECT * FROM [sometable] ORDER BY [column1], [column2] DESC;
Rather than specifying each column in a separate line, you can pass in multiple columns at once
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.AddAll();
query.AddOrderByColumns("column1", "column2", "column3");
// Example Output:
SELECT * FROM [sometable] ORDER BY [column1], [column2], [column3] ASC;
You can specify the order per column
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.AddAll();
query.AddOrderBy("column1", OrderBy.ASCENDING);
query.AddOrderBy("column2", OrderBy.DESCENDING);
// Example Output:
SELECT * FROM [sometable] ORDER BY [column1] ASC, [column2] DESC;
You can join multiple tables
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.AddAll();
query.AddJoin("table2", "column1", "column2", JoinType.INNER);
// Example Output:
SELECT * FROM [sometable]
INNER JOIN [table2] ON [sometable].[column1] = [table2].[column2]; ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.AddAll();
query.AddJoin("table2", "column1", "column2",
"table3", "column3",
"table4", "column4", JoinType.INNER);
// Example Output:
SELECT * FROM [sometable]
INNER JOIN [table2] ON [sometable].[column1] = [table2].[column2]
INNER JOIN [table4] ON [table3].[column3] = [table4].[column4];You can specify the join type. The example below does an OUTER join
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("sometable");
query.AddAll();
query.AddJoin("table2", "column1", "column2",
"table3", "column3",
"table4", "column4", JoinType.OUTER);
// Example Output:
SELECT * FROM [sometable]
FULL OUTER JOIN [table2] ON [sometable].[column1] = [table2].[column2]
FULL OUTER JOIN [table4] ON [table3].[column3] = [table4].[column4];You can use the IInsertQuery to generate INSERT statements. The INSERT SQL will automatically handle object types and convert them to the appropriate SQL output (such as dates, text, strings, etc.). It will also change the syntax to match the corresponding database.
IInsertQuery query = QueryFactory.CreateInsertQuery(DbType.SQLSERVER);
query.SetTable("someTable");
query.Add("dateColumn", DateTime.Now);
query.Add("stringColumn", "some text");
query.Add("numericColumn", 12);
// Example Sql Server Output:
INSERT INTO [someTable]
( [dateColumn], [stringColumn], [numericColumn] )
VALUES ( '3/3/2006 10:10:10 AM', 'some text', 12 )
// Example Access Output:
INSERT INTO [someTable]
( [dateColumn], [stringColumn], [numericColumn] )
VALUES ( #3/3/2006 10:10:10 AM#, 'some text', 12 )
// Example Oracle Output:
INSERT INTO someTable
( dateColumn , stringColumn , numericColumn )
VALUES ( '3/3/2006 10:10:10 AM', 'some text', 12 )
To insert a NULL value, just use the AddNull method and pass in the column name.
IInsertQuery query = QueryFactory.CreateInsertQuery(DbType.SQLSERVER);
query.SetTable("someTable");
query.AddNull("someColumn");
query.AddNull("someColumn2");
// Example Sql Server Output:
INSERT INTO [someTable]
( [someColumn], [someColumn2] )
VALUES ( NULL, NULL )
// Example Access Output:
INSERT INTO [someTable]
( [someColumn], [someColumn2] )
VALUES ( NULL, NULL )
// Example Oracle Output:
INSERT INTO someTable
( someColumn, someColumn2 )
VALUES ( NULL, NULL )
To use a parametized query, use the standard Add method but don't provide a value. A parametized value will automatically be applied.
IInsertQuery query = QueryFactory.CreateInsertQuery(DbType.SQLSERVER);
query.SetTable("someTable");
query.Add("someColumn");
query.Add("someColumn2");
// Example Sql Server Output:
INSERT INTO [someTable]
( [someColumn], [someColumn2] )
VALUES ( @someColumn, @someColumn2 )
// Example Access Output:
INSERT INTO [someTable]
( [someColumn], [someColumn2] )
VALUES ( ?, ? )
// Example Oracle Output:
INSERT INTO someTable
( :someColumn, :someColumn2 )
VALUES ( NULL, NULL )
You can use the IUpdateQuery to generate UPDATE statements. The UPDATE SQL will automatically handle object types and convert them to the appropriate SQL output (such as dates, text, strings, etc.). It will also change the syntax to match the corresponding database.
IUpdateQuery query = QueryFactory.CreateUpdateQuery(DbType.SQLSERVER);
query.SetTable("someTable");
query.Add("dateColumn", DateTime.Now);
query.Add("stringColumn", "some text");
query.Add("numericColumn", 12);
// Example Sql Server Output:
UPDATE [someTable]
SET [dateColumn] = '3/3/2006 10:10:10 AM',
[stringColumn] = 'some text',
[numericColumn] = 12
// Example Access Output:
UPDATE [someTable]
SET [dateColumn] = #3/3/2006 10:10:10 AM#,
[stringColumn] = 'some text',
[numericColumn] = 12
// Example Oracle Output:
UPDATE someTable
SET dateColumn = '3/3/2006 10:10:10 AM',
stringColumn = 'some text',
numericColumn = 12
To insert a NULL value, just use the AddNull method and pass in the column name.
IUpdateQuery query = QueryFactory.CreateUpdateQuery(DbType.SQLSERVER);
query.SetTable("someTable");
query.AddNull("someColumn");
query.AddNull("someColumn2");
// Example Sql Server Output:
UPDATE [someTable] SET [someColumn] = NULL, [someColumn2] = NULL
// Example Access Output:
UPDATE [someTable] SET [someColumn] = NULL, [someColumn2] = NULL
// Example Oracle Output:
UPDATE [someTable] SET someColumn = NULL, someColumn2 = NULL
To use a parametized query, use the standard Add method but don't provide a value. A parametized value will automatically be applied.
IUpdateQuery query = QueryFactory.CreateUpdateQuery(DbType.SQLSERVER);
query.SetTable("someTable");
query.Add("someColumn");
query.Add("someColumn2");
// Example Sql Server Output:
UPDATE [someTable] SET [someColumn] = @someColumn, [someColumn2] = @someColumn2
// Example Access Output:
UPDATE [someTable] SET [someColumn] = ?, [someColumn2] = ?
// Example Oracle Output:
UPDATE someTable SET someColumn = :someColumn, someColumn2 = :someColumn2
Using the IDeleteQuery is extremely simple
IDeleteQuery query = QueryFactory.CreateDeleteQuery(DbType.SQLSERVER);
query.SetTable("someTable");
// Example Output
DELETE FROM someTable
The previous sections showed you how to create basic SELECT, INSERT, UPDATE and DELETE statements. Often the most important part though is the WHERE clause. The ICriteria interface is provided to support criteria creation.
Once you've created your query, then create your criteria and add it by using the SetCriteria method.
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.ACCESS);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddLike("productName", "%.NET%");
query.SetCriteria(criteria);
Console.WriteLine(query.Statement);
// Output:
SELECT * FROM [products]
WHERE [productName] LIKE '%.NET%';
The ICriteria interface provides numerous options. Below are several examples:
You can use AddBetween to find records with a column value between numbers, dates, etc.
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddBetween("productId", 1, 5);
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] BETWEEN 1 AND 5
To specify the opposite, use the AddNotBetween method
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddNotBetween("productId", 1, 5);
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] NOT BETWEEN 1 AND 5
You can use AddEqualTo to find records with a column value between numbers, dates, etc.
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddEqualTo("productId", 1);
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] = 1To do the opposite, use the AddNotEqualTo method
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddNotEqualTo("productId", 1);
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] <> 1Instead of specifying a value, you can use a parametized query
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddNotEqualTo("productId");
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] <> @productIdYou can use AddEqualTo to find records with a column value between numbers, dates, etc.
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddEqualTo("productId", 1);
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] = 1To do the opposite, use the AddNotEqualTo method
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddNotEqualTo("productId", 1);
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] <> 1The sql IN keyword allows you to pass in multiple values at once. So, instead of doing this:
SELECT * FROM Products WHERE productId = 1 OR productId = 2 OR productId = 3
You can instead do this:
SELECT * FROM Products WHERE productId IN (1, 2, 3)
You can also use subqueries with the IN statement:
SELECT * FROM Products WHERE productId IN (
SELECT productId FROM Orders WHERE customerId = 5)To do this using the SQL API, there are two options: pass in a collection or a subquery.
IN Using a Collection
ArrayList al = new ArrayList();
al.Add(1);
al.Add(2);
al.Add(3);
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = CriteriaFactory.CreateCriteria(DbType.SQLSERVER);
criteria.AddIn("productId", al);
query.SetCriteria(criteria);
// Output:
SELECT * FROM products WHERE productId IN (1, 2, 3)
IN Using a Subquery
ISelectQuery subQuery = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
subQuery.SetTable("orders");
subQuery.Add("productId");
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = CriteriaFactory.CreateCriteria(DbType.SQLSERVER);
criteria.AddIn("productId", subQuery);
query.SetCriteria(criteria);
// Output:
SELECT * FROM products WHERE productId IN (SELECT productId FROM orders)
To do the opposite, use the AddNotIn method, which also accepts a subquery or collection.
A greater than query
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddGreaterThan("productId", 1);
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] > 1A query for greater than or equal to
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddGreaterThanOrEqualTo("productId", 1);
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] >= 1A less than query
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddLessThan("productId", 1);
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] < 1A query for less than or equal to
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddLessThanOrEqualTo("productId", 1);
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] <= 1To check for a NULL value, use the AddIsNull method
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddIsNull("productId");
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] IS NULLFor the opposite, use the AddNotNull method
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddNotNull("supplierId", 1);
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [supplierId] IS NOT NULLSo far we've demonstrated how to add single criteria. It's possible to add multiple criteria using the AND and OR keywords.
Using AND
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddEqualTo("productId", 1);
criteria.AddAnd();
criteria.AddEqualTo("lastName", "Schmoe");
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] = 1 AND [lastName] = 'Schmoe'Using OR
ISelectQuery query = QueryFactory.CreateSelectQuery(DbType.SQLSERVER);
query.SetTable("products");
query.AddAll();
ICriteria criteria = query.CreateCriteria();
criteria.AddEqualTo("productId", 1);
criteria.AddOr();
criteria.AddEqualTo("lastName", "Schmoe");
query.SetCriteria(criteria);
// Output:
SELECT * FROM [products] WHERE [productId] = 1 OR [lastName] = 'Schmoe'