Teradata SQL parameter syntax - sql

Is there syntax which allows a parameter marker in the middle of a table name? For example, consider the queries
sel * from t?x
and
sel * from t?x_blah.
Both execute as
sel * from t1
if the user inputs 1. In the first query x = 1 and in the second query x_blah = 1. I would like to modify the second query to set x = 1 and execute as
sel * from t1_blah.
Is there a way to do this?
Thanks!

A question mark parameter marker can only be used for data values, not object names. So, the short answer is no.
Here's some info from Teradata:Clicky!

What's your client tool?
SQL Assistant supports parameters for object names, but there's no way to get the expected behavior (as you probably noticed).
The only solution might be using Dynamic SQL within a Stored Procedure.

A ? works in Teradata SQL Assistant. It will ask you to enter the parameter:
select ?x from ?y;
When you run it, SQL Assistant will ask you for the parameters x and y. If you put 10 instances of ?x in your code, SQL Assistant will only ask for x once.

Related

How to use variables in SQL queries on DataGrip (Exasol dialect)?

Database: EXASOL
IDE: IntelliJ DataGrip
I am trying to declare variables in SQL and call them throughout the query.
This is the equivalent in Microsoft SQL Server:
DECLARE #var AS INT = 3
SELECT #var AS var
-- Use case example:
SELECT * FROM table1 WHERE column_value = #var
Is this possible in DataGrip and Exasol? I searched the documentation (General Script Language, Database Interaction) of Exasol where they describe the following:
a = 3
SELECT :a
However, this opens a console where I am asked to type the value of a. I don't want to type the values of variables every time I execute the code. I want to set a variable and use it on different parts of the query, just like any other high-level programming language.
I found two similar questions on JetBrains' forum (1, 2) but they are unanswered. Another one found on StackOverflow (url) just stated that the dialect is not supported on DataGrips.
Does anyone know how to solve this? Is it simply not supported? It would really increase productivity for me and my team.
Thank you in advance!
After spending some time, I found out that this is not possible. Instead Exasol allows LUA scripts that can run such calculations. Below you will find an example:
CREATE LUA SCRIPT "TEST" (p_country) RETURNS TABLE AS
local param_c = p_country
exit(
query(
[[
SELECT * FROM SCHEMA_NAME.TABLE_NAME
WHERE SK_COUNTRY = :local_c;
]]
,{local_c=param_c}
)
);
/
EXECUTE SCRIPT SCHEMA_NAME.TEST('DE');
In this example the keyword RETURNS TABLE outputs the table results from this query. The keyword exit() is similar to a print() method. And lastly, I don't know why but the function parameter needs to be assigned to a local variable, which then needs to be assigned to another variable in the query. This makes no sense to me, but I could not get it to work otherwise.
In my example I have the script parameter p_country which is assigned to the local parameter param_c which is then assigned to the query parameter local_c.
You can find the documentation under:
https://docs.exasol.com/database_concepts/scripting/general_script_language.htm?Highlight=for%20loop
https://docs.exasol.com/database_concepts/scripting/db_interaction.htm

SSIS save value as a parameter

I am using SELECT UpdateDate FROM dbo.log command in a execute sql task. I'm fairly new to this so please bear with me. I want to store the value as a variable then pass that into the where clause of a subsequent data flow. My questions are:
What is the correct way to setup the Execute SQL Task. In General I have the OLE DB Connection and direct input with the query above. Result Set is set to Single row and then I am storing this to a variable I have created called User:: UpdateDate. For some reason this doesn't work?
I then want to call this date in a data flow. ie. SELECT * FROM Users WHERE RecordDate > User::UpdateDate. I believe the syntax is different for this.
I would really appreciate some help with this. Many thanks in advance
In your Execute SQL Task Editor, configure the Parameter Mapping as shown below, obviously use your own variable, in this example I'm using PackageStartTime.
Then in your SQL statement, use below:
SELECT * FROM Users WHERE RecordDate > ?
To save value from a SQL Statement, you will need to set the Result Set to single row and configure result set as shown in the example below:
Execute SQL Task with ResultSet
First of all, create a variable of type System.Date example: #[User::UpdateDate].
Add an Execute SQL Task select the OLEDB connection and use the following command as SQL Statement:
SELECT TOP 1 UpdateDate FROM dbo.log
Set the ResultSet property to Single Row and in the ResultSet Tab add a Row with the following values:
ResultName = 0 (which means the first column)
VariableName = #[User::UpdateDate]
Additional Information
SSIS Basics: Using the Execute SQL Task to Generate Result Sets
OLEDB Source with parameterized SQL Command
Inside the Data Flow Task, add an OLEDB Source, select the Access Mode to SQL Command. And write the following command:
SELECT * FROM Users WHERE RecordDate > ?
Click on the Parameters button and map the variable #[User::UpdateDate] as the first parameter.
Additional Information
Map Query Parameters to Variables in a Data Flow Component
Parameterized OLEDB source query

SQL Injection without direct user input

In order to prevent SQL Injection for my site, i have used prepared statements.
Now let's say i use somewhere in my code, a simple SQL query like this :
SELECT DATA FROM DATABLE;
Is this code prone to injection ? Well it seems to me that's not possible to be, as there is no user input.But i just want to be sure.
If your statement is fixed (has no outside parameters), then it is immune to injection.
So if your code looks something like this:
result = RunQuery("SELECT * FROM Table")
then you are safe, since the query will always be the same everytime and cannot be influenced by users.
Inject is only possible if you use a variable in your query.
If you use prepaired statements with params it is not possible.
select * from user where id = ?
You cannot change this query, only the value, in that case you will just get no results
If you use
select * from user where id = '$id'
now depending on the value of $id we can have a sql inject.
If $id would be "0' or id > 0 " you will allways login ;)

performance of parameterised SQL

I have a query like
SELECT *
FROM myTable
WHERE key LIKE 'XYZ'
The value 'XYZ' is entered by users (and may include % and _)
If I construct the query using string concatenation it runs in 10 seconds.
But this is unsafe, and I should use a parameterised query.
So I'm constructing the query using the odbc command object and it's execute method, and passing a parameter.
SELECT *
FROM myTable
WHERE key LIKE ?
Unfortunately the parameterised SQL execute method takes a full minute.
This query is one of many that are part of a drill-down / investigation package, and I've had similar slow downs with all the parameterised queries (compared to string concatenation).
How do I find out where the time is going (and fix it) ?
Here's my guess without further information.
I've had similar problems on SQL Server. In SQL Server when the column on your table is 'varchar' and the parameterised query parameter is 'nvarchar' (or vice versa), this causes SQL Server to ignore an available index because the parameter type doesn't match the index type, which in turn results in a table scan.
It's possible the same thing happens for Sybase. If you can see the generated query you can confirm if there's a type mismatch.
If this is the case, then two solutions would be
explicitly set the type of the parameter to match the column type
change the type of the column to match the parameter type being generated
Mitch had the right suggestion.
I had to change the connection string to use the OLEDB driver, then I could set the options:
Optimize Prepare=None
Select Method=Direct

whats the syntax for params in a DB2 query

in MS-SQL I can do something like this
#myVar AS int;
#myVar = 12;
SELECT * FROM table WHERE field = #myVar;
this totally bombs out in DB2 - and I'm not sure if it's RDBMS specific or if it's because I've FUBAR'd the syntax...
Any help is appreciated
there are a limited number of things you can do dynamically in db2 sql compared to ms-sql. most of the syntax for what you appear to be attempting is reserved for use only in a procedure in db2. see the documentation here http://publib.boulder.ibm.com/infocenter/db2luw/v9r5/topic/com.ibm.db2.luw.sql.ref.doc/doc/r0004240.html for what you can do dynamically in db2.
if you are ok supplying parameter value on the fly just use
select * from table where field = ?; when you run it, it will ask you to supply a value for the parm.
If you are using ADO.NET Data Provider to connect to the DB2 Express-C, you can prefix bound SQL parameters with #.
I'm not sure about other DB2 environments, but common symbols used in other databases are: : and ?, so it might be worth trying one of those.