MS SQL Query to base SQL - sql

I am looking to have the following query run on any database (right now it uses MSSQL):
SELECT * FROM mytable
WHERE 0<DATEDIFF(day, ISNULL(DateTwo, DateONE), getdate())
AND othercolumn != 'WUBAN'
Is there anyway to do this in a generic way?

No, there is no generic way to do this.
If you support different DB engines you have to execute the proper SQL statement for each engine. Date functions differ on the individual DB engines and for this particular query there is no generic solution that works on all systems.

If DateTwo and DateOne are parameters, then you are able to do the following calculation in your application:
DATEDIFF(day, ISNULL(DateTwo, DateONE), getdate())
and use the result in your query. If not, I can not see a way.

Related

PROGRESS SYNTAX USING OPENQUERY FOR DATEADD EQUIVALENT

I have an open query I am using to connect to a PROGRESS ODBC, I cannot get the syntax equivalent from SQL of
SELECT DATEADD(DAY, -1, GETDATE())
The Progress SQL documentation is here:
https://documentation.progress.com/output/OpenEdge117/openedge117/#page/dmsrf%2Fadd-months.html%23wwID0EGGFR
There is no DATEADD() function although there is ADD_MONTHS(). I'm not much of a SQL coder but I expect that you could probably cobble something together with the other date related functions.
I came up with the following to get records where the date is greater than two days prior:
where tr_date =
to_date({ fn convert (month(curdate()), sql_varchar)} + '/' + { fn convert(dayofmonth(curdate()) -2, sql_varchar)} + '/' + { fn convert (year(curdate()), sql_varchar)})
It heavily relies on curdate() which you apparently can't use in a select statement, only in a where clause.
In SQL Server I would have done all of this in front of the query, put the results in a variable and then used the variable in the query's where clause, but Progress also apparently doesn't have the concept of variables.
The problem with the above is that it doesn't account for the beginning of the month where substracting 2 from 1 would result in -1 and therefore an invalid date. So the algorithm to account for this becomes more complicated. All more doable if you had variables but trickier when you have to do it all on the fly.
My purpose was to generate a new query each day for an incremental data integration process using SSIS. I switched over to dynamically generating the query in SQL Server and inserting the results into an SSIS configuration table that the package reads. With that method you end up using good ol' reliable dateadd in SQL Server. That unfortunately doesn't help much if you're trying to do this in Progress with SQL there.

SQL: to_char alternative for Oracle AND SQL-Server

I have some sql statements, which i am using for Oracle. This sql statements are used by a programm from me.
I want to support Oracle and SQL-Server with my program without having different sql statements for Oracle and SQL-Server.
Which alternative can i use for the specific Oracle SQL-Statements:
to_char(FIELDNAME, 'YYYY')
to_char(FIELDNAME, 'YYYYMMDD')
to_char(FIELDNAME, 'DD.MM.YYYY')
The sql statements have to work for Oracle and SQL-Server.
Even if at a first glance the SQL implementation from two different vendors looks similar, when working with real life enterprise applications you will stumble upon a large number of differences, and I am only talking about SQL, when comparing PL/SQL with T-SQL there is hardly any resemblance left.
When trying to reduce the usage of two databases to only common functionality, you will loose a lot of their power, you could as well use a txt file on the file system.
One elegant solution, as someone already suggested, would be to leave the columns in the database as DATE data type and extract your data in the application code that stands above the database, if any. For example, in Java, you will map your database DATE columns to java.sql.Date no matter if that date comes from Oracle or from SQL Server.
Still, if you want to get your formatted data from the database, you could create separate columns that hold the formatted date, for example :
FIELDNAME | FIELDNAME_YYYY | FIELDNAME_YYYYMMDD | FIELDNAME_DDMMYYYY
I don't think there are common functions to do what you want. Oracle supports the ANSI standard extract() function for extracting date parts. SQL Server has separate functions for YEAR(), MONTH(), and DAY(). Oracle uses TO_CHAR(); SQL Server uses CONVERT().
One option is to define the functions YEAR(), MONTH(), and DAY() in Oracle and then use string concatenation (via the CONCAT()) function to combine the data. Or, write specific functions in each database for what you want to do. Or, perhaps, someone has implemented TO_CHAR() in SQL Server and you can grab the code from the web.
Finally i found a solution. Maybe its useful some other people too.
You can set the input format for a date...
Oracle: ALTER SESSION SET NLS_DATE_FORMAT = 'DD.MM.YYYY'
SQL-Server: SET DATEFORMAT dmy

Identify DBMS from dialect SQL syntax?

I'm working with a third party API for which I have no documentation. There is a method that takes a SQL string and returns a resultset. Based on valid SQL syntax, I want to identify the SQL DBMS vendor, product and version.
Syntax that works as expected as part of a valid SELECT query:
CASE WHEN 1 = 1 THEN 1 ELSE 0 END
CAST('Catatonic' AS CHAR(3))
GETDATE()
CONVERT(VARCHAR(10), GETDATE(), 101))
SELECT TOP 1 valid_column FROM ValidTable
Syntax that causes syntax errors:
COALESCE(NULL, 'Dog')
ISNULL(NULL, 'Dog')
CURRENT_TIMESTAMP
SELECT ##VERSION
SELECT version()
statements terminated by ; (though this could be an API thing)
Any other SQL syntax to try?
My attempt at an answer, given your tests and the comments above:
Tell the 3rd-party that hosts the API, as well as your boss and/or customer, that you cannot work with an API that does not have documentation, and you MUST have further support from the API vendor to perform your work effectively.
If the documentation says "ANSI SQL Compliant", then that is obviously not true, since your tests include various (well thought-out) instances that would seem to suggest SQL Server, but obviously do not support all queries that SQL Server itself would allow.
So, the 3rd party is apparently filtering, re-parsing, or otherwise modifying the SQL you provide to it, and without further information about what that layer is and what it does/doesn't do, you're hands are more or less tied, and your limited to guesswork and trial-and-error.

MS Access SQL Server DB - Query Syntax for CAST Function

I have converted an Access db (.mdb) to SQL Server. In the meantime I still need to use Access as a front end until new application forms are constructed. Can someone tell me what I might do to fix the situation where:
In Access 2007, a query such as:
SELECT *
FROM TransactionTotals
WHERE TransactionTotals.[Date]= Date()
ORDER BY TransactionTotals.EntryID DESC;
worked, however since the Date() function will not work with SQL Server, with help in a previous post the correct syntax is:
SELECT *
FROM TransactionTotals
WHERE TransactionTotals.[Date]= CAST(GETDATE() AS DATE)
ORDER BY TransactionTotals.EntryID DESC;
BUT! Although the code above will work in a direct SQL Server query (SQL Management Studio), it will be tossed out in Access with a Syntax Error response on the WHERE clause.
Can something be done in Access so I can still run my query bound forms.
I usually do exactly what you do, Access first before migration to SQL server. Access has some really weird syntax compared to server type databases especially when it comes to JOIN clauses and dates, GETDATE() only works on SQL Server, in Access, try this...
SELECT *
FROM TransactionTotals
WHERE TransactionTotals.[Date]= Format(NOW(),"General Date")
ORDER BY TransactionTotals.EntryID DESC;
Feel free to change the format of the date, with or without time.

Dynamically building WHERE clauses in SQL statements

I have a question regarding SQL. I have the following SQL statement:
SELECT id, First, Last, E_Mail, Notes
FROM mytable
WHERE SOMETHING_SHOULD_BE_HERE IS NOT NULL;
I know that the SOMETHING_SHOULD_BE_HERE should be a column(attribute) in my table. Is their a way I can put a variable that can refer to the column I'm trying to access? In my case their are 30 columns. Can I have a string for SOMETHING_SHOULD_BE_HERE that can be assigned in my program to the column in which I want to search?
Thanks
No. Variables in SQL can refer to data, but not to object names (columns, functions or other database objects).
If you are building the SQL query, you'll need to use string operations to build your query.
The column can't be variable, but the value of the column can. The parser needs to know what to bind to.
If you elaborate on what you're trying to solve and which platform you're using it would allow for more complete answers.
You can have different SQLs queries in your code and use each one according to the case.
Another way is generate dynamically the query according the fields you want.
Without dynamic SQL, this is probably your best bet:
SELECT
id, first, last, email, notes
FROM
My_Table
WHERE
CASE #column_name_variable
WHEN 'column_1' THEN column_1
WHEN 'column_2' THEN column_2
...
ELSE 'not null'
END IS NOT NULL
There might be some issues with data type conversions, so you might need to explicitly cast all of the columns to one data type (VARCHAR is probably the best bet). Also, there's a good chance that performance will be horrendous on this query. I'd test it thoroughly before even thinking about implementing something like this.
I mentioned this in my comment, but for completeness I'll put it here too... you can probably also accomplish this with dynamic SQL, but how you do that will depend on your database server (MS SQL Server, Oracle, mySQL, etc.) and there are usually some caveats to using dynamic SQL.
In JDBC program, yes,the select statement can be composed like string operation.
for(String colName: colList)
{
String sql="Select id, First, Last, E_Mail, Notes From mytable where "+colName+" IS NOT NULL";
//execute the sql statement
}
It depends on how you are going to find out the value of SOMETHING_SHOULD_BE_HERE.
If you are in an Oracle PLS/SQL environment you could build up the WHERE clause using dynamic SQL and then use EXECUTE IMMEDIATE to execute it.
If you have a small set number of possibilities you could use CASE to workaround your problem possibly.
Your question is unclear.
However I am quite sure that what you have in mind is the so-called dynamic SQL (and related). "Dynamic SQL" allows you to dynamically build and submit queries at runtime. However such functionalities may not exist for your RDBMS.
There are several ways to do this.
When your query would return one and only one row
then you have to consider the EXECUTE IMMEDIATE statements (along with sp_executesql in tSQL : http://msdn.microsoft.com/en-us/library/ms188001.aspx ; or the USING clause in PL/SQL : http://docs.oracle.com/cd/B14117_01/appdev.101/b10807/13_elems017.htm to specify a list of input/output bind arguments) and/or PREPARED statements (http://rpbouman.blogspot.fr/2005/11/mysql-5-prepared-statement-syntax-and.html).
When your query can return more than one row
then you have to consider techniques such as the EXECUTE IMMEDIATE statement with the BULK COLLECT INTO clause or the OPEN-FOR, FETCH, and CLOSE statements (explicit cursors in PL/SQL :
http://docs.oracle.com/cd/B28359_01/appdev.111/b28370/dynamic.htm)
Please note that except in some particular cases, most conventional techniques like IF-THEN-ELSE and CASE statements should be preferred (along with a good algorithm). Furthermore they work with almost all RDBMS.