How to create an APEX_COLLECTION? - oracle-sqldeveloper

I want to create an apex_collection in the Oracle SQL Developer for my apex webapplication.
Here's my code:
apex_collections.create_or_truncate_collection('TEST');
After running the statement I get the following:
If I enter the select-statement:
SELECT *
FROM apex_collections
WHERE collection_name = 'TEST';
afterwards, I get this:
It seems to me that no collection has been created,although there is no error code. What am I doing wrong? Why is the collection not created? I also tried to run the statement in the SQL Workshop of Oracle APEX, but the command is unknown there. I am using Oracle 12c version.

You will need a valid APEX session to create the collection. If you are on APEX 18.1 or later, use the procedure apex_session.create_session (see documentation) to create one. Make sure that the app_id is valid for the workspace that your schema is assigned to.
For anything before 18.1, OraOpenSource oos-utils has a procedure that does the same: oos_util_apex.create_session (see code). You will need to install oos-utils, or at least compile this package in your schema. Alternatively, replicate the activity contained in this procedure.
Update: Also, I just noticed Jeff Smith's comments. You will need to add members to the collection in order to get meaningful results.
begin
apex_session.create_session(
p_app_id => 100
, p_page_id => 1
, p_username => 'somebody'
);
end;
/
select * from apex_collections; -- shows nothing
begin
apex_collection.create_or_truncate_collection(
p_collection_name => 'test'
);
apex_collection.add_member(
p_collection_name => 'test'
, p_c001 => 'test row'
);
end;
/
select * from apex_collections; -- shows one record
Also, if you are using SQLDEV to troubleshoot the collections in an APEX session, then you'll want to use either the apex_session.attach or oos_util_apex.join_session procedure, depending on the version of APEX you are running. Use the APEX Session ID assigned to your browser session.
HTH.

Related

How can I see the sql statement of a view (db resides on AWS)

I've just installed the vscode extension (Oracle Developer Tools for VS Code (SQL and PLSQL)
) and successfully connected the db.
The db resides on AWS.
I can connect the db and just wanted to test it by opening an existing view.
But, it just lets me "describe" the view. So I can see the columns but I need to edit the query statement.
What's missing? Or is the problem the AWS part?
I usually use SQL Developer but I'm furthermore interested in backing up the work via git commits. And I like the way "git graph" extensions presents the changes.
DDL view_name
Or
SELECT
text_vc
FROM
dba_views
WHERE
owner = :schema AND
view_name = :view_name;
With help from someone of the Oracle community I managed to get it working.
Basic query is:
select
dbms_metadata.get_ddl('VIEW', 'VIEW_NAME', 'VIEW_OWNER')
from
dual;
So, in my case it is:
select
dbms_metadata.get_ddl('VIEW', 'ALL_DATA_WAREHOUSE_BOSTON', 'WHB')
from
dual;
Owner is the name you fill in when connection to the database, which is the key/value pair (username/password).
If you are not sure who the owner of the view is, check it with this query:
select owner from ALL_VIEWS where VIEW_NAME ='ALL_DATA_WAREHOUSE_BOSTON';

SQL Server OpenQuery() behaving differently then a direct query from TOAD

The following query works efficiently when run directly against Oracle 11 using TOAD (with native Oracle drivers)
select ... from ... where ...
and srvg_ocd in (
select ocd
from rptofc
where eff_endt = to_date('12/31/9999','mm/dd/yyyy')
and rgn_nm = 'Boston'
) ...
;
The exact same query "never" returns if passed from SQL Server 2008 to the same Oracle database via openquery(). SQL Server has a link to the Oracle database using an Oracle Provider OLE DB driver.
select * from openquery( servername, '
select ... from ... where ...
and srvg_ocd in (
select ocd
from rptofc
where eff_endt = to_date(''12/31/9999'',''mm/dd/yyyy'')
and rgn_nm = ''Boston''
) ...
');
The query doesn't return in a reasonable amount of time, and the user kills the query. I don't know if it would eventually return with the correct result.
This result where the direct TOAD query works efficiently and the openquery() version "never" returns is reproducible.
A small modification to the openquery() gives the correct efficient result: Change eff_endt to trunc(eff_endt).
That is well and good, but it doesn't seem like the change should be necessary.
openquery() is supposed to be pass through, so how can there be a difference between the TOAD and openquery() behavior?
The reason we care is because we frequently develop complex queries with TOAD directly accessing Oracle. Once we have the query functioning and optimized, we convert it to an openquery() string for use in a SQL Server application. It is extremely aggravating to have a query suddenly fail with openquery() when we know it worked as a direct query. Then we have to search for a work-around through trial and error.
I would like to see the Oracle trace files for the two scenarios, but the Oracle server is within another organization, and we are not getting cooperation from the Oracle DBAs.
Does anyone know of any driver, or TOAD, or ??? issues that could account for the discrepancy? Is there any way to eliminate the problem such that both methods always give the same result?
I know you asked this a while ago but I just came across your question.
I agree, they should be the same. Obviously there is a difference. We need to find out where the difference is.
I am thinking out loud as I type...
What happens if you specify just a few column instead of select * from openquery?
How many rows are supposed to be returned?
What if, in the oracle select, you limit the returned rows?
How quickly does the openquery timeout?
Are TOAD and SS on the same machine? Are you RDPing into the SS and running toad from there?
Are they using the same drivers? including bit? (32/64) version?
Are they using the same account on oracle?
It is interesting that using the trunc() makes a difference. I assume [eff_endt] is one of the returned fields?
I am wondering if SS is getting all the rows back but it is choking on doing the date conversions. The date type in oracle may need to be converted to a ss date type before ss shows it to you.
What if you insert the rows from the openquery into a table where the date field is just a (n)varchar. I am thinking ss might just dump the date it is getting back from oracle into that text field without trying to convert it.
something like:
insert into mytable(f1,f2,f3,datetimeX)
select f1,f2,f3,datetimeX from openquery( servername, '
select f1,f2,f3,datetimeX from ... where ...
and srvg_ocd in (
select ocd
from rptofc
where eff_endt = to_date(''12/31/9999'',''mm/dd/yyyy'')
and rgn_nm = ''Boston''
) ...
');
What if toad or ss is modifying the query statement before sending it to oracle. You could fire up wireshark and see what toad and ss are actually sending.
I would be very curious if you get this resolved. I link ss to oracle often and have not run into this issue.
Here are basic things you can check for to see what the database is doing after it receives the query. First, check that the execution plans are the same in TOAD as when the query runs using openquery. You could plan the query yourself in TOAD using:
explain plan set statement_id = 'openquery_test' for <your query here>;
select *
from table(dbms_xplan.display(statement_id => 'openquery_test';
then have someone initiate the query using openquery() and have someone with permissions to view v$ tables to run:
select sql_id from v$session where username = '<user running the query>';
(If there's more than one connection with the same user, you'll have to find an additional attribute to isolate the row representing the session running the query.)
select *
from table(dbms_xplan.display_cursor('<value from query above'));
If those look the same then I'd move on to checking database waits and see what it's stuck on.
select se.username
, sw.event
, sw.p1text
, sw.p2text
, sw.p3text
, sw.wait_time_micro/1000000 as seconds_in_wait
, sw.state
, sw.time_since_last_wait_micro/1000000 as seconds_since_last_wait
from v$session se
inner join
v$session_wait sw
on se.sid = sw.sid
where se.username = '<user running the query>'
;
(again, if there's more than one session with the same username, you'll need another attribute to whittle it down to the one you're interested in.)
If the plans are different, then you need to find out why, or if they're the same, look into what it's waiting on (e.g. SQL*Net message to client ?) and why.
I noticed a difference using OLEDB through MS Access (2013) connecting to Oracle 10g & 11g tables, in that it did not always recognize indexes or primary keys on the Oracle tables properly. The same query through an MS Access 2000 database (using odbc) worked fine / had no problem with indexes & keys. The only way I found to fix the OLEDB version was to include all of the key fields in the SELECT -- which was not a satisfying answer, but it's all I could find. This might be an option to try through SSMS / OpenQuery(...) as well.
Besides that... you can try some alternatives to OPENQUERY, such as:
4-part names: SELECT ... FROM Server..Schema.Table
Execute AT: EXEC ('select...') at linked server
But as for why the OLEDB provider works differently than the native Oracle Provider -- the providers are not identical, and the native provider would be more likely to pave-over Oracle quirks than the more generic OLEDB provider would.

Transaction context in use by another session

I have a table called MyTable on which I have defined a trigger, like so:
CREATE TRIGGER dbo.trg_Ins_MyTable
ON dbo.MyTable
FOR INSERT
AS
BEGIN
SET NOCOUNT ON;
insert SomeLinkedSrv.Catalog.dbo.OtherTable
(MyTableId, IsProcessing, ModifiedOn)
values (-1, 0, GETUTCDATE())
END
GO
Whenever I try to insert a row in MyTable, I get this error message:
Msg 3910, Level 16, State 2, Line 1
Transaction context in use by another session.
I have SomeLinkedSrv properly defined as a linked server (for example, select * from SomeLinkedSrv.Catalog.dbo.OtherTable works just fine).
How can I avoid the error and successfully insert record+execute the trigger?
Loopback linked servers can't be used in a distributed transaction if MARS is enabled.
Loopback linked servers cannot be used in a distributed transaction.
Trying a distributed query against a loopback linked server from
within a distributed transaction causes an error, such as error 3910:
"[Microsoft][ODBC SQL Server Driver][SQL Server]Transaction context in
use by another session." This restriction does not apply when an
INSERT...EXECUTE statement, issued by a connection that does not have
multiple active result sets (MARS) enabled, executes against a
loopback linked server. Note that the restriction still applies when
MARS is enabled on a connection.
http://msdn.microsoft.com/en-us/library/ms188716(SQL.105).aspx
I solve It.
I was using the same linked server to call the second procedure and then into the procedure I was using the same linked server.
It's very Easy, only we have to know the restricctions of linked servers.
I have resolved it by removing linked server used in the stored procedure and then called stored procedure by the same linked server. It wasnt working in DEV environement.
One of causes of this situation is a trigger that works for linked-sever database table. An also SQL version of SQL-Server which processes database matters. To avoid this ERROR during sql query execution we should temporarily disable and after execution enable triggers for tables updated. All with database name check. Here is an example:
Select * From People where PersonId In (#PersonId, #PersonIdRight)
IF 'DOUBLE' = DB_NAME()
ALTER TABLE [dbo].[PeopleSites] DISABLE TRIGGER [PeopleSites_ENTDB_UPDATE]
Update PeopleSites Set PersonId = #PersonIdRight Where PersonId = #PersonId
IF 'DOUBLE' = DB_NAME()
ALTER TABLE [dbo].[PeopleSites] ENABLE TRIGGER [PeopleSites_ENTDB_UPDATE]
Select * From PeopleSites where PersonId In (#PersonId, #PersonIdRight)
I also got the same error in our DEV environemnt, moving the linked databases to another sql instance resolved the issue. In our production environment these databases are already on separate instances
In my case I was using SQL 2005 and got "transaction context in use by another session" when running Insert....exec over a linked server. The fix for me was to patch from SP2 build 3161 to SP3. SP2 cumulative 5 is supposed to fix though.
https://support.microsoft.com/en-us/kb/947486
When remote database sits on the same server,configure the linked server without specifying the database server ip / hostname and port. Just the database name should be sufficient.
I was getting the same "transaction context in use by another session error" when trying to run an UPDATE query:
BEGIN TRAN
--ROLLBACK TRAN
--COMMIT TRAN
UPDATE did
SET did.IsProcessed = 0,
did.ProcessingLockID = NULL
FROM [proddb\production].DLP.dbo.tbl_DLPID did (NOLOCK)
WHERE did.dlpid IN ('bunch of GUIDs')
--WHERE did.DLPID IN (SELECT DLPID FROM #TableWithData)
However I didn't realize I was already trying to run this on the DLP database on the ProdDb\Production server. Once I removed that "[proddb\production].DLP.dbo." prefix from the query, it worked fine.

How do I store a set of queries inside PostgreSQL so I can easily run it again?

I want to save a set of queries (multiple SQL updates) as a single element that I can execute using pgAdmin3 (PostgreSQL 9.1).
I know that I can save single SELECTS as views but how about multiple UPDATE queries?
Example:
BEGIN;
UPDATE ...;
UPDATE ...;
COMMIT;
Update: What I looking for is a step-by-step guide of adding a stored procedure using the GUI, not running a SQL query that creates it.
So far, I encountered two problems with "New function...": the return type is required and found that NULL is not acceptable, so tried integer. Also, set the type to SQL but I don't know what exactly to write inside the SQL tab, whatever I try the OK button is still disabled and the statusbar says: Please enter function source code.
Do you know or did you try stored procedure (well, stored-procedure-like functions) ?
http://www.postgresql.org/docs/9.1/interactive/plpgsql-structure.html
To call it
select <name of function>(<param1>, <param2>) as result;
Here is the missing guide for a basic SQL stored procedure, one that does return 1.
right click on Functions and choose New Function...
complete name as my_procedure, return type as integer, language as sql
select Definition tab and write SELECT 1;
done
It would be nice to know if you can create queries that are returning nothing.

Execute Stored Process with pass in SQL query from another table?

Currently my development environment is using SQL server express 2008 r2 and VS2010 for my project development.
My question is like this by providing a scenario:
Development goal:
I develop window services something like data mining or data warehousing using .net C#.
That meant I have a two or more database involved.
my senario is like this:
I have a database with a table call SQL_Stored inside provided with a coloum name QueryToExec.
I first idea that get on my mind is written a stored procedure and i tried to came out a stored procedure name Extract_Sources with two parameter passed in thats ID and TableName.
My first step is to select out the sql need to be execute from table SQL_Stored. I tried to get the SQL by using a simple select statement such as:
Select Download_Sql As Query From SQL_Stored
Where ID=#ID AND TableName=#TableName
Is that possible to get the result or is there another way to do so?
My Second step is to excecute the Sql that i get from SQL_Stored Table.Is possible to
to execute the query that select on the following process of this particular stored proc?
Need to create a variable to store the sql ?
Thank you,Appreciate for you all help.Please don't hesitate to voice out my error or mistake because I can learn from it. Thank you.
PS_1:I am sorry for my poor English.
PS_2:I am new to stored procedure.
LiangCk
Try this:
DECLARE #download_sql VARCHAR(MAX)
Select
#download_sql = Download_Sql
From
SQL_Stored
Where
AreaID = #AreaID
AND TableName = #TableName
EXEC (#download_sql)