ORA-01747: invalid user.table.column, table.column, or column specification - oracle

Get the above error when the execute immediate is called in a loop
Update CustomersPriceGroups set 1AO00=:disc Where cuno=:cuno
Parameters: disc=66 cuno=000974
Update CustomersPriceGroups set 1AP00=:disc Where cuno=:cuno
Parameters: disc=70.5 cuno=000974
Update CustomersPriceGroups set 1AQ00=:disc Where cuno=:cuno
Parameters: disc=66 cuno=000974
Update CustomersPriceGroups set 1ZA00=:disc Where cuno=:cuno
Parameters: disc=60 cuno=000974
What does this mean ?
Here is the code fragment
c:=PriceWorx.frcPriceListCustomers('020','221');
LOOP
fetch c into comno,cuno,nama,cpls;
exit when c%notfound;
dbms_output.put_Line(cuno);
g:=priceWorx.frcPriceListItemGroups('020','221');
d:=priceworx.frcCustomerDiscounts('020','221',cuno);
loop
fetch g into comno,cpgs,n;
fetch d into comno,cpls,cuno,cpgs,stdt,tdat,qanp,disc,src;
--dbms_output.put(chr(9)||cpgs);
sQ:='Update saap.CustomersPriceGroups set "'|| trim(cpgs)||'"=:disc '
|| ' Where cuno=:cuno';
execute immediate sQ using disc,cuno;
commit;
dbms_output.put_line( sQ );
dbms_output.put_line( chr(9)||'Parameters: disc='|| disc||' cuno='||cuno);
exit when g%notfound;
end loop;
close g;
close d;
end loop;

check your query for double comma.
insert into TABLE_NAME (COLUMN1, COLUMN2,,COLUMN3) values(1,2,3);
(there is extra comma after COLUMN2).
Update: recently (some people have special talents) i succeed to get same exception with new approach:
update TABLE_NAME set COLUMN1=7, set COLUMN2=8
(second SET is redundant)

Unquoted identifiers must begin with an alphabetic character (see rule 6 here). You're trying to assign a value to a column with a name starting with a number 1AO00, 1AP00 etc.
Without seeing the table definition for CustomersPriceGroups we don't know if it has columns with those names. If it does then they must have been created as quoted identifiers. If so you'll have to refer to them (everywhere) with quotes, which is not ideal - makes the code a bit harder to read, makes it easy to make a mistake like this, and can be hard to spot what's wrong. Even Oracle say, on the same page:
Note: Oracle does not recommend using quoted identifiers for database
object names. These quoted identifiers are accepted by SQL*Plus, but
they may not be valid when using other tools that manage database
objects.
In you code you appear to be using quotes when you assign sQ, but the output you show doesn't; but it doesn't have the saap. schema identifier either. That may be because you're not running the version of the code you think, but might just have been
lost if you retyped the data instead of pasting it - you're not showing the earlier output of c.cuno either. But it's also possible you have, say, the case of the column name wrong.
If the execute is throwing the error, you won't see the command being executed that time around the loop because the debug comes after it - you're seeing the successful values, not the one that's breaking. You need to check all the values being returned by the functions; I suspect that g is returning a value for cpgs that actually isn't a valid column name.
As #ninesided says, showing more information, particularly the full exception message, will help identify what's wrong.

It means that the Oracle parser thinks that one of your columns is not valid. This might be because you've incorrectly referenced a column, the column name is reserved word, or because you have a syntax error in the UPDATE statement that makes Oracle think that something which is not a column, is a column. It would really help to see the full statement that is being executed, the definition of the CustomersPriceGroups table and the full text of the exception being raised, as it will often tell which column is at fault.

if you add a extra "," at the end of the set statement instead of a syntax error, you will get ORA-01747, which is very very odd from Oracle
e.g
update table1
set col1 = 'Y', --this odd 1
where col2 = 123
and col3 = 456

In addition to reasons cited in other answers here, you may also need to check that none of your table column names have a name which is considered a special/reserved word in oracle database.
In my case I had a table column name uid. uid is a reserved word in oracle and therefore I was getting this error.
Luckly, my table was a new table and I had no data in it. I was a able to use oracle DROP table command to delete the table and create a new one with a modified name for the problem column.
I also had trouble with renaming the problem column as oracle wouldn't let me and kept throwing errors.

You used oracle keyword in your SQL statement

And I was writing query like. I had to remove [ and ]
UPDATE SN.TableName
SET [EXPIRY_DATE] = systimestamp + INTERVAL '12' HOUR,
WHERE [USER_ID] ='12345'
We recently moved from SQL Server to Oracle.

The cause may also be when you group by a different set of columns than in select for example:
select tab.a, tab.b, count(*)
from ...
where...
group by tab.a, tab.c;

ORA-01747: invalid user.table.column, table.column, or column
specification
You will get when you miss the column relation when you compare both column id your is will not be the same check both id in your database
Here is the sample Example which I was facing:
UPDATE TABLE_NAME SET APPROVED_BY='1000',CHECK_CONDITION=ID, WHERE CONSUMER_ID='200'
here Issue you will get when 'CHECK_CONDITION' and 'ID' both column id will no same
If both id will same this time your query will execute fine, Check id Id both Column you compare in your code.

For me, the issue was due to use to column name "CLUSTER" which is a reserved word in Oracle. I was trying to insert into the column. Renaming the column fixed my issue.
insert into table (JOB_NAME, VERSION, CLUSTER, REPO, CREATE_TS) VALUES ('abc', 169, 'abc.war', '1.3', 'test.com', 'test', '26-Aug-19 04.27.09.000000949 PM')
Error at Command Line : 1 Column : 83
Error report -
SQL Error: ORA-01747: invalid user.table.column, table.column, or column specification

In my case, I had some.* in count. like count(dr.*)

Related

How to create Oracle Spatial Index?

I am trying to create an Oracle Spatial index but seeing strange behavior.
I have a table in my schema as follows:
CREATE TABLE "Event" (
"EventID" NUMBER(32,0) GENERATED ALWAYS AS IDENTITY INCREMENT BY 1 START WITH 1 NOT NULL,
"Name" NVARCHAR2(30),
"Location" "SDO_GEOMETRY" NOT NULL,
CONSTRAINT "PK_EVENT" PRIMARY KEY ("EventID")
) ;
This works fine and I know I have to create an entry in user_sdo_geom_metadata, that works as you would expect with the following:
insert into user_sdo_geom_metadata (table_name,column_name,diminfo,srid) values ('Event','Location',
sdo_dim_array(sdo_dim_element('X',-180.0,180.0, 0.005),sdo_dim_element('Y',-90.0,90.0, 0.005)), 4326);
This reports success and when I do a select on user_sdo_geom_metadata I see the row. However, when I try to create the spatial index with:
CREATE INDEX "EVINDEX" ON "Event" ("Location") INDEXTYPE IS MDSYS.SPATIAL_INDEX_V2
I get the following error:
SQL Error [29855] [99999]: ORA-29855: error occurred in the execution of ODCIINDEXCREATE routine
ORA-13203: failed to read USER_SDO_GEOM_METADATA view
ORA-13203: failed to read USER_SDO_GEOM_METADATA view
ORA-06512: at "MDSYS.SDO_INDEX_METHOD_10I", line 10
The weird thing is the Index looks like it's been created.
select * from all_indexes where table_name='Event';
Shows the index??? The other odd thing is when I do a select * on ALL_SDO_GEOM_METADATA, no rows are returned??? I'm connecting as a user with almost every privilege and role but not as SYSDBA. I can't get my head around this one.
UPDATE
Incredibly, this seems to be a case sensitivity issue. If you change the table and column names to all UPPERCASE it works. It seems my neverending disappointment in Oracle has a whole new chapter. Going to try to struggle through this somehow, but like most things with Oracle, it's one unrelenting slog to get anything done :(
The documentation says:
The table name cannot contain spaces or mixed-case letters in a quoted string when inserted into the USER_SDO_GEOM_METADATA view, and it cannot be in a quoted string when used in a query (unless it is in all uppercase characters).
and
The column name cannot contain spaces or mixed-case letters in a quoted string when inserted into the USER_SDO_GEOM_METADATA view, and it cannot be in a quoted string when used in a query (unless it is in all uppercase characters).
However, it also says:
All letters in the names are converted to uppercase before the names are stored in geometry metadata views or before the tables are accessed. This conversion also applies to any schema name specified with the table name.
which you can see if you query the user_sdo_geom_metadata view after your insert; the mixed-case names have become uppercase EVENT and LOCATION.
But then:
Note: Letter case conversion does not apply if you use mixed case (“CamelCase”) names enclosed in quotation marks. However, be aware that many experts recommend against using mixed-case names.
And indeed, rather unintuitively, it seems to work if you include the quotes in the user_sdo_geom_metadata insert:
insert into user_sdo_geom_metadata (table_name,column_name,diminfo,srid)
values (
'"Event"',
'"Location"',
sdo_dim_array(sdo_dim_element('X',-180.0,180.0, 0.005),
sdo_dim_element('Y',-90.0,90.0, 0.005)), 4326
);
db<>fiddle
So it appears that the values from the view are at some point concatenated into a dynamic SQL statement, which would explain some of the behaviour.

Oracle Alter command to rename existing Column errorring

alter table tablename rename column zl_divn_nbr to div_loc_nbr;
Error while executing the above statement. Please help.
SQL Error: ORA-54032: column to be renamed is used in a virtual column expression
54032. 0000 - "column to be renamed is used in a virtual column expression"
*Cause: Attempted to rename a column that was used in a virtual column
expression.
*Action: Drop the virtual column first or change the virtual column
expression to eliminate dependency on the column to be renamed
Run the following SQL query in your database using the table name mentioned in the error message. For example, in the error message shown in this article, the table name is 'tablename'. Note that whilst the table name appears in lower case in the error message, it may be upper case in your DB. This query is case sensitive so if you receive no results, check whether the table name is upper case inside your database.
SELECT COLUMN_NAME, DATA_DEFAULT, HIDDEN_COLUMN
FROM USER_TAB_COLS
WHERE TABLE_NAME = 'tablename';
Before proceeding, make sure the Bitbucket Server process is not running. If Extended Statistics has been enabled, contact your database administrator to have them drop the Extended Statistics metadata from the table, and proceed with your upgrade. If you wish to enable Extended Statistics again after the upgrade you may do so, however be aware that you may need to repeat this process again for subsequent upgrades otherwise you risk running into this issue again.
Removing columns created by Extended Statistics requires using an in-build stored procedure,
DBMS_STATS.DROP_EXTENDED_STATS().
Usage of this stored procedure is covered further in ORA-54033 and the Hidden Virtual Column Mystery, and looks similar to the following:
EXEC DBMS_STATS.DROP_EXTENDED_STATS(ownname=>'<YOUR_DB_USERNAME>', tabname=>'tablename', extension=>'("PR_ROLE", "USER_ID", "PR_APPROVED")')
References
Database Upgrade Eror: column to be rename
Thanks.
Probably, you have such a table :
CREATE TABLE tablename(
id NUMBER,
zl_divn_nbr NUMBER,
zl_divn_percent NUMBER GENERATED ALWAYS AS (ROUND(zl_divn_nbr/100,2)) VIRTUAL
);
where zl_divn_nbr column is used for a computation for virtual(zl_divn_percent) column.
To rename zl_divn_nbr, all referenced virtual columns to this column should be removed, and may be created later.
The syntax for defining a virtual column is this :
column_name [datatype] [GENERATED ALWAYS] AS (expression) [VIRTUAL]
Since version 11 R1, we have this property.
ALTER TABLE rename column to
In the case of tables with virtual or 'group extension columns' the above
statement returns an error before Oracle 12cR2. For Oracle 12cR2 or newer versions the above statement runs fine cause 'renaming column' command is decoupled from the group extension aspect.

Can I use an Oracle trigger to force a varchar column to fit column width?

I have an application which is occasionally being passed data which causes it to fail with ORA-12899 error trying to insert the record into a varchar(2000) column on an Oracle 11g database. )In some cases it is trying to insert a field of more than 4000 characters.)
In the longer term, I will request a change to the application to prevent this happening, but meanwhile I need a short-term fix to allow the record to be saved, truncating the data to 2000 characters.
I've experimented with a "before insert" trigger (which works fine when truncating it from say 1500 to 1000 characters), but what I've found is that where the data is more than 2000 characters (i.e. more than the column length) the insert still fails with ORA-12899.
Is there any way round this, other than changing the database column to a CLOB?
Include the case statement similar to the following code in your insert command
insert into test_table
(column1)
values
(
(case when length('ablekkkkkkkkkkkh') > 2000 then substr('ablekkkkkkkkh',1,2000)
else 'ablekkkkkkkkkkkh' end )
);

Comparing Date column to sysdate yields: a non-numeric character was found where a numeric was expected

I've been having a strange issue where the comparison of a date column to SYSDATE yields the following error:
01858. 00000 - "a non-numeric character was found where a numeric was expected"
*Cause: The input data to be converted using a date format model was
incorrect. The input data did not contain a number where a number was
required by the format model.
*Action: Fix the input data or the date format model to make sure the
elements match in number and type. Then retry the operation.
I'm re-creating a MATERIALIZED VIEW; which included some minor changes, and whenever the process aborts it always points to the '>=' in the following derived table query:
SELECT id,
desc,
start_date,
end_date
FROM T_LIPR_POLICY_ROLE TLPR
WHERE end_date >= SYSDATE
Now end_date is a type DATE, and I can actually execute this query by itself, but whenever I try to run it in the materialized view it always aborts with the error above. Although last week I was able to create it with the same query.
Any ideas?
Thank you,
Hi I'm terribly sorry for the long delay. I just couldn't post the whole statement for security reasons.
Now the issue has been resolved. The problem was that our materialized view script was aggregating data from 17 different places vía a UNIONs. Now for some reason the error was pointing to wrong line of code (see below).
SELECT id,
desc,
start_date,
end_date
FROM T_LIPR_POLICY_ROLE TLPR
WHERE end_date >= SYSDATE <-- ORACLE POINTS TO THIS LINE
Now this was like the tenth statement in the script, but the error really was in the sixth statement in the script; which was obviously misleading. In this statement a particular record (out of millions) was attempting the following operation:
to_date(' / 0/ ') <-- This was the cause of the problem.
Note that this text wasn't like this in the actual script it literally said to_date(<column name of type varchar>), but 2 records out of 15 million had the text specified above.
Now what I don't quite get is why Oracle points to the wrong line of code.
¿Is it an Oracle issue?
¿Is it a problem with the SQL Developer?
¿Could it be a conflict with a hint? We use several like this: /*+ PARALLEL (init 4) */
Thank you for all your help.
Is desc a column name? If yes then you are using a oracle reserved keyword desc as a column name.
SELECT id,
desc,---- here
start_date,
end_date
FROM T_LIPR_POLICY_ROLE TLPR
WHERE end_date >= SYSDATE
We cannot use oracle reserved keywords in column names.
Please change the column name.

plsql for inserting a table

declare
dno number(4);
dname varchar2(5);
ddate date;
dbasic number(10);
djob varchar2(15);
dcomm number(5);
dept number(5);
dmgr number(5);
begin
select empno,ename,hiredate,sal,job1,comm,deptno,mgr
into dno,dname,ddate,dbasic,djob,dcomm,dept,dmgr
from emp
where empno=&userno;
if sql%rowcount>0
then
insert into newempl
values(dno,dname,djob,dmgr,ddate,dbasic,dcomm,dept);
dbms_output.put_line('records inserted into it');
dbms_output.put_line(dno||' '||dname||' '||ddate||' '||dbasic);
end if;
end;
Error report:
ORA-01858: a non-numeric character was found where a numeric was expected
ORA-06512: at line 19
01858. 00000 - "a non-numeric character was found where a numeric was expected"
*Cause: The input data to be converted using a date format model was
incorrect. The input data did not contain a number where a number was
required by the format model.
*Action: Fix the input data or the date format model to make sure the
elements match in number and type. Then retry the operation.
I do not understand what the error is.
From the error message it looks like you're inserting values into the wrong columns. Without seeing your table structure (from describe newmpl for example) this is a bit of a guess, but this statement:
insert into newempl
values(dno,dname,djob,dmgr,ddate,dbasic,dcomm,dept);
... is assuming that the columns in the newempl table are in a certain order, which may not be (and appears to not be) the case. More specifically here, I think it's complaining about hiredate, as you're implicitly putting the djob value in that column - assuming the new table looks like emp - and the djob value can't be converted into a date.
Update based on comment: from how you said you created the table, this is equivalent to:
insert into newempl(dno, dname, ddate, dbasic, djob, dcomm, dept, dmgr)
values(dno,dname,djob,dmgr,ddate,dbasic,dcomm,dept);
... so as you can see when it's laid out like that the columns are not aligned, and you are indeed trying to put your djob value into the ddate column, which won't work.
It is always safer to explicitly specify the columns, both to prevent problems with different ordering in different environments (though that shouldn't really happen with controlled code) and to prevent this breaking if a new column is added. Something like:
insert into newempl(empno,ename,jon1,mgr,hiredate,sal,comm,deptno)
values(dno,dname,djob,dmgr,ddate,dbasic,dcomm,dept);
As an aside, when declaring your local variables you could specify them based on the table, for example dno emp.empno%TYPE. And as another aside based on your comment, I'd recommend giving local variables different names to the table columns to avoid confusion.
As a_horse_with_no_name said, this can be done with a simple SQL insert, and even within a PL/SQL block it doesn't need separate select and insert statements; you could just do:
insert into newempl(empno,ename,jon1,mgr,hiredate,sal,comm,deptno)
select empno,ename,jon1,mgr,hiredate,sal,comm,deptno
from emp
where empno=&userno;
Unfortunately none of this addresses the requirement that 'the employees who are managers must be inserted into new table', since you aren't doing anything with the mgr column. I don't think it would be constructive to do that part of the task for you at this point though, and I'm not sure where &userno fits in to that.

Resources