Main Page | Report this Page
Computers Forum Index  »  Computer - Databases - Oracle (Misc)  »  Is this the sanctioned way to ascertain a table's...
Page 1 of 2    Goto page 1, 2  Next

Is this the sanctioned way to ascertain a table's...

Author Message
Ramon F Herrera...
Posted: Fri Oct 16, 2009 11:32 pm
Guest
All my database accesses are done through Pro*C/C++.

Sometimes my code needs to verify whether a table exists. Years ago, I
was about to post that particular questions here. I then realized
that the following statements achieve the desired results:

EXEC SQL SELECT COUNT(1) INTO :howMany FROM user_tables WHERE
table_name = :table_name;

if (howMany == 1)
doThis();
else
doThat();

Is that "the" proper way?

-Ramon
 
Ramon F Herrera...
Posted: Fri Oct 16, 2009 11:51 pm
Guest
On Oct 16, 7:32 pm, Ramon F Herrera <ra... at (no spam) conexus.net> wrote:
Quote:
All my database accesses are done through Pro*C/C++.

Sometimes my code needs to verify whether a table exists. Years ago, I
was about to post that particular  questions here. I then realized
that the following statements achieve the desired results:

EXEC SQL SELECT COUNT(1) INTO :howMany FROM user_tables WHERE
table_name = :table_name;

if (howMany == 1)
    doThis();
else
   doThat();

Is that "the" proper way?

-Ramon


Since the following question is conceptually similar to the previous,
I will tag it along this thread.

I need to write code which creates a new record if it doesn't exist
and modifies it otherwise. It seems that Oracle (actually, the SQL
language) has two different statements for doing this, one being
INSERT and the other UPDATE, right? (IOW, there is no single command
like "create or replace" - I have to roll my own "create or replace").

Therefore, my code should probably look like this:

SELECT COUNT(1) INTO howMany FROM mytable WHERE <some constraint>

if (howMany == 1)
UPDATE mytable ();
else
INSERT INTO mytable();

Right?

I just want to make sure that that is the correct way.

TIA,

-Ramon
 
joel garry...
Posted: Fri Oct 16, 2009 11:56 pm
Guest
On Oct 16, 4:48 pm, Shakespeare <what... at (no spam) xs4all.nl> wrote:
Quote:
Ramon F Herrera schreef:



All my database accesses are done through Pro*C/C++.

Sometimes my code needs to verify whether a table exists. Years ago, I
was about to post that particular  questions here. I then realized
that the following statements achieve the desired results:

EXEC SQL SELECT COUNT(1) INTO :howMany FROM user_tables WHERE
table_name = :table_name;

if (howMany == 1)
    doThis();
else
   doThat();

Is that "the" proper way?

-Ramon

I always get a bit worried if an application has to check whether a
table exists.... should they not be there just by design?

Shakespeare

I think it is reasonable for many applications, they can ascertain
where in a process things are or whether they are being run for the
first time. Now, I'm a great believer in the DBA being in control of
DDL, and I think you are right to worry, I'm just saying it isn't
necessarily in the nightmare realm.

As far as the proper way, TIMTOWTDI.

jg
--
at (no spam) home.com is bogus.
yay, boss is going fishing! That means I can... have more work to
do... boo.
 
Dan Blum...
Posted: Fri Oct 16, 2009 11:59 pm
Guest
In comp.databases.oracle.misc Ramon F Herrera <ramon at (no spam) conexus.net> wrote:
Quote:
Since the following question is conceptually similar to the previous,
I will tag it along this thread.

I need to write code which creates a new record if it doesn't exist
and modifies it otherwise. It seems that Oracle (actually, the SQL
language) has two different statements for doing this, one being
INSERT and the other UPDATE, right? (IOW, there is no single command
like "create or replace" - I have to roll my own "create or replace").

Therefore, my code should probably look like this:

SELECT COUNT(1) INTO howMany FROM mytable WHERE <some constraint

if (howMany == 1)
UPDATE mytable ();
else
INSERT INTO mytable();

Right?

I just want to make sure that that is the correct way.

Take a look at the MERGE statement.

--
_______________________________________________________________________
Dan Blum tool at (no spam) panix.com
"I wouldn't have believed it myself if I hadn't just made it up."
 
joel garry...
Posted: Fri Oct 16, 2009 11:59 pm
Guest
On Oct 16, 4:51 pm, Ramon F Herrera <ra... at (no spam) conexus.net> wrote:

Quote:

I need to write code which creates a new record if it doesn't exist
and modifies it otherwise. It seems that Oracle (actually, the SQL
language) has two different statements for doing this, one being
INSERT and the other UPDATE, right? (IOW, there is no single command
like "create or replace" - I have to roll my own "create or replace").

Therefore, my code should probably look like this:

SELECT COUNT(1) INTO howMany FROM mytable WHERE <some constraint

if (howMany == 1)
 UPDATE mytable ();
else
 INSERT INTO mytable();

Right?

I just want to make sure that that is the correct way.

http://asktom.oracle.com/pls/asktom/f?p=100:11:0::::P11_QUESTION_ID:61865893444475

jg
--
at (no spam) home.com is bogus.
http://www.theregister.co.uk/2009/10/16/ibm_intel_insider_trading/
 
Ramon F Herrera...
Posted: Sat Oct 17, 2009 12:03 am
Guest
On Oct 16, 7:48 pm, Shakespeare <what... at (no spam) xs4all.nl> wrote:
Quote:
Ramon F Herrera schreef:



All my database accesses are done through Pro*C/C++.

Sometimes my code needs to verify whether a table exists. Years ago, I
was about to post that particular  questions here. I then realized
that the following statements achieve the desired results:

EXEC SQL SELECT COUNT(1) INTO :howMany FROM user_tables WHERE
table_name = :table_name;

if (howMany == 1)
    doThis();
else
   doThat();

Is that "the" proper way?

-Ramon

I always get a bit worried if an application has to check whether a
table exists.... should they not be there just by design?

Shakespeare


Good point. The thing about my design is that I have "a table of
tables". The code in question is for my internal use, and I type it
from the Unix prompt. Let's say I have a bunch of company clients and
the command in question tells me when was the last time such company
made a payment or something.

For policy and other reasons I treat every company as a separate
entity with their own tables. Some companies demand not to share table
space with other companies.

Therefore the interaction would look like this:

% last_payment google

The program -after checking that a table named "google" does not
exist- will retort:

"Are you kidding me, Ramon? `google' is not your client"

-RFH
 
Ramon F Herrera...
Posted: Sat Oct 17, 2009 12:25 am
Guest
On Oct 16, 7:56 pm, joel garry <joel-ga... at (no spam) home.com> wrote:
Quote:
On Oct 16, 4:48 pm, Shakespeare <what... at (no spam) xs4all.nl> wrote:



Ramon F Herrera schreef:

All my database accesses are done through Pro*C/C++.

Sometimes my code needs to verify whether a table exists. Years ago, I
was about to post that particular  questions here. I then realized
that the following statements achieve the desired results:

EXEC SQL SELECT COUNT(1) INTO :howMany FROM user_tables WHERE
table_name = :table_name;

if (howMany == 1)
    doThis();
else
   doThat();

Is that "the" proper way?

-Ramon

I always get a bit worried if an application has to check whether a
table exists.... should they not be there just by design?

Shakespeare

I think it is reasonable for many applications, they can ascertain
where in a process things are or whether they are being run for the
first time.  Now, I'm a great believer in the DBA being in control of
DDL, and I think you are right to worry, I'm just saying it isn't
necessarily in the nightmare realm.

As far as the proper way, TIMTOWTDI.

jg
--
at (no spam) home.com is bogus.
yay, boss is going fishing!  That means I can... have more work to
do... boo.


I obviously agree with joel, and would like to put the Great Bard's
worries to rest.

My applications create a whole bunch of SQL statements on the fly,
using C++. Assembling those SQL statements is an expensive task,
computationally speaking. Therefore, even before my code embarks into
the task of preparing a set of complex query(es), it should make sure
that at least the basic table (called 'google' in my previous example)
exists.

Let me use an actual real example. I hate getting inside the "sqlplus"
shell with the fury of 1K suns. I am a clumsy typist and am used to
modern shells. Therefore I wrote a handy utility called 'nrec', which
I run from the Unix prompt:

% nrec table_this
% 1242

% nrec table_that
% 5639

Internally, the command 'nrec' actually is a simple:

SELECT COUNT(1) from :someTable;

The user can type (or mistype) any table name, which should be checked
before attempting to perform the actual COUNT. Let's say that I prefer
to handle errors on my own instead of feeding crap to Oracle.

-Ramon
 
Shakespeare...
Posted: Sat Oct 17, 2009 3:48 am
Guest
Ramon F Herrera schreef:
Quote:
All my database accesses are done through Pro*C/C++.

Sometimes my code needs to verify whether a table exists. Years ago, I
was about to post that particular questions here. I then realized
that the following statements achieve the desired results:

EXEC SQL SELECT COUNT(1) INTO :howMany FROM user_tables WHERE
table_name = :table_name;

if (howMany == 1)
doThis();
else
doThat();

Is that "the" proper way?

-Ramon


I always get a bit worried if an application has to check whether a
table exists.... should they not be there just by design?

Shakespeare
 
Shakespeare...
Posted: Sat Oct 17, 2009 12:50 pm
Guest
Ramon F Herrera schreef:
Quote:
On Oct 16, 7:48 pm, Shakespeare <what... at (no spam) xs4all.nl> wrote:
Ramon F Herrera schreef:



All my database accesses are done through Pro*C/C++.
Sometimes my code needs to verify whether a table exists. Years ago, I
was about to post that particular questions here. I then realized
that the following statements achieve the desired results:
EXEC SQL SELECT COUNT(1) INTO :howMany FROM user_tables WHERE
table_name = :table_name;
if (howMany == 1)
doThis();
else
doThat();
Is that "the" proper way?
-Ramon
I always get a bit worried if an application has to check whether a
table exists.... should they not be there just by design?

Shakespeare


Good point. The thing about my design is that I have "a table of
tables". The code in question is for my internal use, and I type it
from the Unix prompt. Let's say I have a bunch of company clients and
the command in question tells me when was the last time such company
made a payment or something.

For policy and other reasons I treat every company as a separate
entity with their own tables. Some companies demand not to share table
space with other companies.

Therefore the interaction would look like this:

% last_payment google

The program -after checking that a table named "google" does not
exist- will retort:

"Are you kidding me, Ramon? `google' is not your client"

-RFH


Ok, fair enough. This seems a legitimate way of checking, as long as
your own scripts are involved. You convinced me!!

Shakespeare
 
Mark D Powell...
Posted: Sat Oct 17, 2009 3:07 pm
Guest
On Oct 17, 7:24 am, Serge Rielau <srie... at (no spam) ca.ibm.com> wrote:
Quote:
Out of principle I would never use COUNT() to check for existence.
Imagine a bowl of rice. does it require counting the rice grains inside
the bowl to know whether it is empty or not?
One glance should be enough.
In SQL Terms that would be an EXISTS predicate.
Or if you want to keep it simple in your case

SELECT 1 FROM USER.TABLES WHERE table_name = :table_name AND ROWNUM < 2

In teh case of USER_TABLE by design you may only get one row, but if you
use COUNT() here chances are someone will copy your code and use it
somewhere else where there are a million buggers to count.

Cheers
Serge

--
Serge Rielau
SQL Architect DB2 for LUW
IBM Toronto Lab

There is an American expression that comes to mind in regards to not
using a select count(*) to verify existance just because some other
developer might copy the code at some future date: you can't fix
stupid.

I do not think I would let what someone might do stop me from doing
what I need to do. What I might do if Serge's concern came to mind is
code a database stored function that perrforms the table exists check
and returns 0 or 1 to indicate existance.

Still, I wonder if there is not a better way to determine what SQL to
compile. If the application has several distinct features then
perhaps an installed feature table by customer could be used to guide
the compile.

HTH -- Mark D Powell --
 
Serge Rielau...
Posted: Sat Oct 17, 2009 3:24 pm
Guest
Out of principle I would never use COUNT() to check for existence.
Imagine a bowl of rice. does it require counting the rice grains inside
the bowl to know whether it is empty or not?
One glance should be enough.
In SQL Terms that would be an EXISTS predicate.
Or if you want to keep it simple in your case

SELECT 1 FROM USER.TABLES WHERE table_name = :table_name AND ROWNUM < 2

In teh case of USER_TABLE by design you may only get one row, but if you
use COUNT() here chances are someone will copy your code and use it
somewhere else where there are a million buggers to count.

Cheers
Serge

--
Serge Rielau
SQL Architect DB2 for LUW
IBM Toronto Lab
 
Maxim Demenko...
Posted: Sat Oct 17, 2009 5:24 pm
Guest
Noons wrote:
Quote:
Ramon F Herrera wrote,on my timestamp of 17/10/2009 9:32 AM:
All my database accesses are done through Pro*C/C++.

Sometimes my code needs to verify whether a table exists. Years ago, I
was about to post that particular questions here. I then realized
that the following statements achieve the desired results:

EXEC SQL SELECT COUNT(1) INTO :howMany FROM user_tables WHERE
table_name = :table_name;

if (howMany == 1)
doThis();
else
doThat();

Is that "the" proper way?

It is most definitely not the proper way.
If you want to check for table existence, you check its meta-data in the
dictionary exists. You do not count the rows!
Imagine what that would do to the performance of your application if all
tables had billions of rows, for example.
Select the table name from the view USER_TABLES or ALL_TABLES, depending
on if the table is owned by the current logon or not, respectively. And
it's either found or not found, period. There is a specific return code
to check for that in Pro*C. It's also a lot faster than counting rows.

I got the impression, he *is* checking metadata (more precise -
user_tables).

at (no spam) OP
i would probably not verify at all whether the table exists. Look at the
demo examples ansidyn1.pc and ansidyn2.pc
($ORACLE_HOME/precomp/demo/proc) - your goal looks for me as typical
use case for dynamic sql. Just parse
the statement, what you intend to execute with the table of interest
(assuming , this table exists) and if the parse fail, do the else branch
of your code. Imho, doing like that, you reduce the work for your engine
to the minimum.

Best regards

Maxim
 
Noons...
Posted: Sat Oct 17, 2009 5:33 pm
Guest
Ramon F Herrera wrote,on my timestamp of 17/10/2009 9:32 AM:
Quote:
All my database accesses are done through Pro*C/C++.

Sometimes my code needs to verify whether a table exists. Years ago, I
was about to post that particular questions here. I then realized
that the following statements achieve the desired results:

EXEC SQL SELECT COUNT(1) INTO :howMany FROM user_tables WHERE
table_name = :table_name;

if (howMany == 1)
doThis();
else
doThat();

Is that "the" proper way?

It is most definitely not the proper way.
If you want to check for table existence, you check its meta-data in the
dictionary exists. You do not count the rows!
Imagine what that would do to the performance of your application if all tables
had billions of rows, for example.
Select the table name from the view USER_TABLES or ALL_TABLES, depending on if
the table is owned by the current logon or not, respectively. And it's either
found or not found, period. There is a specific return code to check for that
in Pro*C. It's also a lot faster than counting rows.
 
Noons...
Posted: Sat Oct 17, 2009 5:34 pm
Guest
Ramon F Herrera wrote,on my timestamp of 17/10/2009 9:51 AM:

Quote:
I need to write code which creates a new record if it doesn't exist
and modifies it otherwise. It seems that Oracle (actually, the SQL
language) has two different statements for doing this, one being
INSERT and the other UPDATE, right? (IOW, there is no single command
like "create or replace" - I have to roll my own "create or replace").

Therefore, my code should probably look like this:

SELECT COUNT(1) INTO howMany FROM mytable WHERE <some constraint

if (howMany == 1)
UPDATE mytable ();
else
INSERT INTO mytable();

Right?

I just want to make sure that that is the correct way.


Check MERGE statement: it was created precisely to cover this situation.
 
Noons...
Posted: Sun Oct 18, 2009 5:15 am
Guest
Maxim Demenko wrote,on my timestamp of 17/10/2009 11:24 PM:


Quote:
at (no spam) OP
i would probably not verify at all whether the table exists. Look at the
demo examples ansidyn1.pc and ansidyn2.pc
($ORACLE_HOME/precomp/demo/proc) - your goal looks for me as typical
use case for dynamic sql. Just parse
the statement, what you intend to execute with the table of interest
(assuming , this table exists) and if the parse fail, do the else branch
of your code. Imho, doing like that, you reduce the work for your engine
to the minimum.


That is indeed the best way to achieve this.
Use the parsing of dynamic sql to handle the
table existence validation. It not only takes
care of existence of table but also does not bypass
any security "hiding" applied by designers.
 
 
Page 1 of 2    Goto page 1, 2  Next
All times are GMT
The time now is Fri Dec 04, 2009 9:27 am