Do we use single colon in postgreSQL? - postgresql

For ex, I have a query in postgreSQL such that "product_version=:productVersion".
It's giving me a syntax error.

It's giving you a syntax error because it makes no sense as SQL, and is invalid syntax.
(Please always show the exact text of error messages*)
Since inserting the string literal :productVersion doesn't make much sense, e.g.
product_version=':productVersion'
you might be using the psql command line client and trying to substitute a client variable. If so, you need to use a quoted substitution, e.g.:
product_version=:'productVersion'
but this only works for psql. Not Rails and the Pg gem, not JDBC, not PHP, not psycopg2, nothing but psql.
If that's not what you meant, then either you are using a programming language with placement parameters and using the wrong parameter syntax for your language, or you are attempting to use the psql command line client's variable substitution and aren't using psql. Impossible to guess what you mean unless you specify the language/tools used.
Look up the placement parameter syntax for your programming language and database driver. Make sure you're using the right one.

Related

Translate PL/SQL define to TSQL

I am given a task to transition PL/SQL code to T-SQL.
Can anybody explain what SET DEFINE ON does in sqlplus and most impooirtantly how to translate it to T-SQL (I suppose using sqlcmd as a launcher?)
SET DEFINE is an SQL*Plus command setting the use and prefix for substitution variables. & is the default prefix and SET DEFINE ON resets it to this default and turns on the use of substitution variables.
So this is not a PL/SQL thing but an SQL*Plus thing.
As far as I know there's no such thing as substitution variables for sqlcmd, i.e. there's no equivalent for sqlcmd let alone T-SQL. But I might be wrong there.
'&' appears to be a token of the metalanguage used by SQL*Plus (the client, that is) to activate its "variable substitution" feature. So string literals containing '&' ("Marks & Spencer") tokens may not behave entirely as expected. SET DEFINE apparently serves to control that activation.

Syntax error at or near /" while using lower()

I am retrieving the following sql statement from a table and then using bind variables to substitute the values in. I get a syntax error when running the statement. It seems to be occurring as a result of the lower() function however I believe I am using this correctly. I have tried running the statement manually via psql and it works fine with the values I provide. Does anyone have any ideas on this one? I have tried switching the ' for $$ but this had no effect.
statement
SELECT column_name
FROM information_schema.columns
WHERE table_name=lower(':1')
and column_name=lower(':2')
expected basic statement with substituted values
SELECT column_name
FROM information_schema.columns
WHERE table_name=lower('MyTableName')
and column_name=lower('MyColumnName')
statement run by postgresql
SELECT column_name
FROM information_schema.columns
WHERE table_name=lower('((E'RWOL_TMA_ROADWORKS'))')
and column_name=lower('((E'TPHS_CWAY_RESTRICT_TYPE'))')
Error in C#
ERROR: 42601: syntax error at or near \"MyTableName\"
Error in PostgreSQL log file
2012-04-16 11:36:15 BST ERROR: syntax error at or near "RWOL_TMA_ROADWORKS" at character 80
2012-04-16 11:36:15 BST STATEMENT: SELECT column_name FROM information_schema.columns WHERE table_name=lower('((E'RWOL_TMA_ROADWORKS'))') and column_name=lower('((E'TPHS_CWAY_RESTRICT_TYPE'))')
EDIT: Retrieval and implementation code is written in C#. I use the database connection base classes and the npgsql provider factory in order to make connections, run queries and retrieve the data. This method works for all other queries that use this method of binding variables etc apart from this one where I try to use the lower() function.
EDIT: I have tried removing the quotes altogether to let the binding agent deal with quoting the values and this provided the same syntax error.
EDIT: Have now enabled logging and added the actual statement that postgresql is running.
I think vyegorov is on the right path - there's something funny with your placeholders.
I don't think your second example is the actual query after substition because that doesn't contain any errors. Where did it come from and why aren't you providing the actual query - do you have statement logging turned on in PostgreSQL?
Also, I'm suspicious of the syntax error - what's going on with the escaped double-quotes? Are they actually double-quotes and not doubled-up single quotes?
Are you sure you need single-quotes around your placeholders? Usually the drivers manage that for you.
Are you sure you aren't double-quoting the values anywhere?
Get the actual SQL and look at the quoting and the problem will be obvious I suspect.
UPDATE: now have SQL
Here's the error in the posted statement:
lower('((E'RWOL_TMA_ROADWORKS'))')
You've got two levels of quotes here. Remove the ones you've added and we should end up with something like:
lower((E'RWOL_TMA_ROADWORKS'))
Ignoring the repeated brackets that's valid (The E'...' is the syntax for a c-style escaped string - google around standard_conforming_strings).
Maybe you shouldn't use quotes around :1 and :2. Most APIs that support bind variables will correctly quote the value for you.
I think that it is not lower() functions' issue, but rather bind variable processing issue.
As #Adrian suggests, try not to use quotes around your bind variables.
And you should also consult your databases logs, you'll see more information there about what's going on.
EDIT: Use:
SHOW data_directory;
SHOW log_directory;
SQL statement to find the locations of your DATA directory and logs location, if logs path is relative, then it will be relative to the DATA directory.
Go there and find the recently modified file, check the contents. You should see the error message with default PostgreSQL configuration.
And it'd be good for you to enable debugging also on the middleware / factory levels.

Hitting ORA-01461 when inserting multibyte characters from perl into oracle

I have a perl script that is inserting records from a text file into our database. Whenever the record has a multibyte character like "RODR_Í_GUEZ". I receive the error ORA-01461, however i'm nowhere near the 4000 characters to switch from varchar2 to long
setting:
$ENV{NLS_CHARACTERSET} = 'AL32UTF8';
before connecting doesn't seem to help.
Using a java client (SQuirreL SQL) and manually writing the INSERT INTO statement inserts the record just fine, so i'm sure it's not how the database is configured.
Any thoughts?
You probably want to set the NLS_LANG environment variable. For Unix-ish systems, there is a script supplied in $ORACLE_HOME/server/bin called nls_lang.sh to output a reasonable value for your system, based on the LANG environment variable.
e.g. for my system (LANG=en_GB.UTF-8) the equivalent Oracle setting is
NLS_LANG=ENGLISH_UNITED KINGDOM.AL32UTF8
More info: http://forums.oracle.com/forums/thread.jspa?threadID=381531
Sergiusz's post there says practically all you need to know: I'll just add that the Perl DBD::Oracle driver is OCI-based, and the pure-Java JDBC driver isn't, hence they work differently in the same environment.

PostgreSQL syntax error eof caused commit

We are working on merging individual files into a group PostgreSQL database. The files have all been working perfectly fine on their own and when we have combined we have run them with no problems. It started to hang on the creation of one trigger, so we commented the trigger out. The next time we ran the merge file we got the following error:
ERROR: Syntax error at end of input
LINE 181: --$$ LANGUAGE plpgsql
Following this error there were subsequent syntax errors and then to our horror we found the following in our log file:
ERROR: Syntax error at end of input
LINE 181: --$$ LANGUAGE plpgsql
COMMIT
We had tests in this file that contained test data that was NOT supposed to be entered into the database, corrupting who knows how much of the data in our database. We have looked through every file included and there is no COMMIT anywhere!
Has anyone ever run into something similar? Is there any reason why an error in parsing would ever cause a commit?
If you don't have a BEGIN statement, then the PostgreSQL connection is in "autocommit" mode, committing each change after the statement is run. Since you're incorrectly commenting your code, I'd say you've commented the BEGIN statement earlier in the code. But I can't be sure because you did not provide any of your SQL.
Note that the syntax:
--$$
does not comment out the end of function $$. What it means is empty comment as the last thing inside a string. It might help you if you read the line as:
--
$$
That is why you're getting a parse error on a "commented" line. If it was actually commented, PostgreSQL would not parse it. $$ is a quote operator enclosing SQL code, and is just a convenience syntax against using ''s for quoting (which would mean you have to double-quote each quote inside the quoted SQL). What you think was a commented out line was actually just a piece of a string ending with two hyphens.
On a general note: You should use commenting only for adding descriptions to the code and not disabling sections of code. Use version control if you need to have access to older versions of the code.
Edit: Clarified explanation on quoted strings. Hope this makes more sense now.

Remote Informix 11.5 Command Line Client

Does a command line tool ship with Informix 11.5 similar to SQLCMD for SQL Server?
If yes, how do I connect to a remote server and perform regular SELECT/INSERT/UPDATE queries using it?
As Michal Niklas says, the standard tool provided with IBM Informix Dynamic Server (colloquially IDS or even just Informix) is DB-Access. However, it is distributed only with IDS itself, not with the Informix Client SDK (CSDK) or Informix Connect (I-Connect) products.
If you want to access IDS from a machine that does not have IDS installed, you need either CSDK or I-Connect on the machine, and some other software - perhaps the original (pre-Microsoft by a decade and more) version of SQLCMD. This is what I use - and have used in various versions over the last (cough, splutter, ouch) twenty-two years or so; I wrote it because I didn't like the command line behaviour of a program called isql (part of the product Informix SQL), which was the pre-cursor to DB-Access. (Lot's of history - not too important to you.)
Usage - SQLCMD has more options than you know what to do with. The basics are simple, though:
sqlcmd -d dbname#dbserver -e 'select * from table' -x -f file.sql
This connects to a database called 'dbname' at the database server known as 'dbserver' as specified in the sqlhosts file (normally $INFORMIXDIR/etc/sqlhosts). The '-e' indicates an SQL expression - a select statement; the results will be printed to standard output in a strict format (Informix UNLOAD format), one logical line per record. The '-x' turns on trace mode; the '-f' option means read the named file for further commands. The '.sql' extension is not mandatory (beware: DB-Access requires the '.sql' extension and will add it for you). (Arguments not prefixed by either '-e' or '-f' are interpreted heuristically; if it contains spaces, it is SQL; if it does not, it is a filename.) The '-H' option prints column headings (labels) before a result set; the '-T' option prints the column types (after the headings, before the results). The '-B' option runs in benchmark mode; it turns on trace, prints the statement, the time when the statement started, and times how long it took. (Knowing when the statement started is helpful if the SQL takes many minutes to run - as it can in benchmarking scenarios). There are controls over the output format (including CSV and even variant of XML - but not an XML using namespaces) and date format, and so on. There are 'built-in' commands to redirect input and output and errors; most command line options can also be used in the interpeter, etc. SQLCMD also provides a history mechanism; it saves SQL statements and you can view, edit or rerun them. In conjunction with output redirection, you can save off a list of statements executed, etc.
The only gotcha with SQLCMD is that it is not currently ported to Windows. It did work on Windows once upon about 6 or 7 years ago. Since then, Microsoft's compilers have gotten antsy about non-MS API functions, insisting that even if I ask for them by name (by requesting POSIX functionality), the functions must be prefixed by an underscore, and by deprecating a bunch of functions that can be used safely if you pay attention to what you are doing (but, regrettably, can be abused by those who are not paying attention, and there are more inattentive than attentive coders around, it seems) - I mean functions like 'strcpy()' which can be used perfectly safely if you know the size of the source and destination strings before you call it. It is on my list of things to do - it just hasn't been done yet because it isn't my itch.
There is also another Open Source tool called SQSL that you can consider. It has some advantages over SQLCMD (conditional logic, etc) but I think SQLCMD has some advantages over SQSL.
You could also consider whether Perl + DBI + DBD::Informix + dbish would work for you.
Try DB-Access
...
DB–Access provides a user interface for entering, executing, and debugging Structured Query Language (SQL) statements and Stored Procedure Language (SPL) routines...