Showing posts with label oracle. Show all posts
Showing posts with label oracle. Show all posts

01 March 2008

Oracle to PostGres Conversion : Delete Row command is not deleting rows

The topic sounds funny. But yeah, the delete row command was not deleting the row as i expected it to be. Luckily i found the solution for the same.
But first, let me post my problem.
I was doing a simple delete operation over some table..

Say for example,
select count(*) from some_table_x where some_col_name = 'some_value'

This query was returning me a value of 1 which meant is exactly one row that matches this clause. I tried firing a delete query like the one below,
delete from some_table_x where some_col_name = 'some_value'

Ofcourse, the output i expected was that the row to get deleted. But instead, i was informed by postgres as "0 rows deleted. Query executed successfully"

This was very annoying as postgres was not throwing any kind of error and my delete query had the 'where' clause same as the select query i used. The only possible place where the problem might haved occured was the triggers. Even constraints can prevent the row from getting deleted. But the delete operation would have intimated me some kindof error.

So, i concluded only triggers may have this issue. When i went through my trigger, it had a code something like this,
CREATE TRIGGER sample_trig
BEFORE INSERT OR UPDATE OR DELETE
ON some_table_x
FOR EACH ROW
EXECUTE PROCEDURE "TRGR_SAMPLE"();

And the trigger function was something like,
CREATE OR REPLACE FUNCTION "TRGR_SAMPLE"()
RETURNS "trigger" AS
$BODY$
BEGIN
IF TG_OP='DELETE'
THEN
-- some operations
END IF;

IF TG_OP='UPDATE'
THEN
-- some operations
END IF;

IF TG_OP='INSERT'
THEN
-- some operations
END IF;

RETURN NEW;
END;
$BODY$
LANGUAGE 'plpgsql' VOLATILE;

The trigger was a BEFORE EACH ROW trigger. It will be fired everytime when one of insert or delete or update operation occurs on some_table_x. The bug in this code was that i was returning NEW at the end of the trigger statement. Whereas in oracle, no one need to worry about what a trigger returns, only need to worry about what a trigger does. But not so in Postgres, you have to write a trigger that calls a trigger function which ofcourse should return either NULL or NEW or OLD.
Since a delete operation does not have a NEW RECORD type, returning NEW does not make any sense at all during a delete operation. So, a small addition to the code really solved the issue.
CREATE OR REPLACE FUNCTION "TRGR_SAMPLE"()
RETURNS "trigger" AS
$BODY$
BEGIN
IF TG_OP='DELETE'
THEN
-- some operations
RETURN OLD;
END IF;


IF TG_OP='UPDATE'
THEN
-- some operations
END IF;

IF TG_OP='INSERT'
THEN
-- some operations
END IF;

RETURN NEW;
END;
$BODY$
LANGUAGE 'plpgsql' VOLATILE;

Although the problem and the solution sounded very simple, finding out that sucked up a lot of time as there was no error been thrown by postgres.

06 February 2008

Successfully Emulated Oracle's connect by prior to postgresql using Java

Friends,

Today, I was successfully able to simulate Oracle's "connect by prior" equivalent SQL to postgresql with a little bit of help from Java. I was fed up with finding a decent solution in the net for using a similar query to connect by prior. I found many options. Top of them being Evgen's connect by patch for Postgresql 8.2/8.3. But that patch comes with a tarball which i need to setup/install which i dont want to do. Another one is using some crawl_tree method given some by guy. That never even came close to working. I was really fed up and finally switched over to my home ground : JAVA. Yeah, connect by prior method simply follows the Depth first search algorithm. You can see the example picture given in the side representing some hierarchical arrangement of data. The Depth first search has to follow the order : D L J I H I A E A I J L K G K F K L D C B. Just trace this path and you will know how this works. After Eliminating the redundant values you will get : DLJIHAEKGFCB which is what connect by does finally.

So implementing this algorithm is a piece of cake and i did too. What i did is, selected all the records from the table "select * from (sometable)". Stored all the values in an ArrayList. Then using two main columns (parent/child Node) , i applied this algorithm. It perfectly worked for me. It gave the exact result what oracle would have given. I even cross verified them side by side using Aquastudio connected to both Oracle and PostgresDB. I guess this idea should be enough in implementing the logic. If you even want the full code, i can do that for ya.
Bye for now from,
Braga

Oracle Spatial query windowing technique

This again is one of the problems i faced while coding in oracle 10g.
I will post both the problem and the solution for it..

Dear friends,
The database i'm using (mvdemo - mapviewer demo DB that comes along with Oracle 10g), has only data about united states. Say if i have my query window like this, -180, 0, 180 , 90 (which is the upper half of the earth), i am getting the desired result. ie.,Here is that query,

SELECT count(s.geom) FROM states s WHERE SDO_FILTER(s.geom,SDO_GEOMETRY(2003,8265,NULL,SDO_ELEM_INFO_ARRAY(1,1003,3),SDO_ORDINATE_ARRAY(-180, 0 , 180, 90))) = 'TRUE';
--Returns 55
I'm currently having a problem with my rectangular window query. When i query with a window value of -180, -90, 180, 90 (which covers the whole earth), the number of spatial objects (SDO_GEOM) that is returned is 0. It is not throwing any ORA error. But the expected result is as usual 55.

SELECT count(s.geom) FROM states s WHERE SDO_FILTER(s.geom,SDO_GEOMETRY(2003,8265,NULL,SDO_ELEM_INFO_ARRAY(1,1003,3),SDO_ORDINATE_ARRAY(-180, 0 , 180, 90))) = 'TRUE';
--Returns 0
Can anyone please help me out with this issue??

Solution
I found the solution to my problem. actually the query given here works just fine.wat i was doing was using the sdo_intersection(, ). The query window am using here is the whole earth. But according to spatial rule, there cant be any geometry greater than half the surface of the earth.
Yes.. its pretty true. Imagine yourself trying to calculate the distance from Pearl harbor to japan. For a small kid, if you give the map and ask him to measure, he'l tell the longest route in the conventional map. But it is not so. We have to calculate the shortest distance which ofcourse will only be possible when you see the earth as a sphere. Oracle 10g is no exception. The design is logically correct. So any query window given exceeds half the size of the earth, oracle will throw an error.