is there another way to do this? I want to restrict the user to his own module and associated results. First intention was to create a view because this gives the possibility to use a WHERE clause in combination with USER which givs me the username of the connected user.
CREATE OR REPLACE FORCE VIEW "ADMIN_STUDENT"."MODULE_LEADER" ("MCODE", "MLECTURER")
AS
SELECT "MCODE",
"MLECTURER"
FROM MODULE
WHERE MLECTURER = USER;
Check out Oracle Virtual Private Database or Oracle Label Security
Alternatively, add use SYS_CONTEXT('USERENV', 'SESSION_USER') in the view definition.
Related
i'm having this situation whereby user are using Dbeaver to access to DB2. There is some views created. At the moment user have the ability to use the Dbeaver to see the view DDL (back end code).
Question : how/is there any way to prevent the user see the view DDL?
much appreciate you advice
Look at the Db2 Obfuscation facility.
CALL DBMS_DDL.CREATE_WRAPPED ('CREATE OR REPLACE VIEW TEST_OBFUSCATED AS SELECT TABNAME FROM SYSCAT.TABLES WHERE TABSCHEMA LIKE ''SYS%''');
SELECT TEXT
FROM SYSCAT.VIEWS
WHERE VIEWSCHEMA = CURRENT SCHEMA AND VIEWNAME = 'TEST_OBFUSCATED';
TEXT
CREATE OR REPLACE VIEW TEST_OBFUSCATED WRAPPED SQL11014 long_meaningless_string
You may use this view as any other one in the same way, but its text is not visible for everyone.
Moreover, you can use this "strange" obfuscated statement to create the view from scratch. There is a scalar function which helps you to get this obfuscated statement without creation it first.
VALUES DBMS_DDL.WRAP ('CREATE OR REPLACE VIEW TEST_OBFUSCATED AS SELECT TABNAME FROM SYSCAT.TABLES WHERE TABSCHEMA LIKE ''SYS%''')
If someone still needs to view the real view text, you may use Row and column access control (RCAC) on the SYSIBM.SYSVIEWS table.
If you want your users to be able to select from a view, they must be able to obtain the definition of that view.
You can wrap the query against the view in a set-returning user-defined function, which has all privileges of its creator, presumably a DBA, and grant other users only the EXECUTE privilege on that function. You will then be able to revoke from your users the privileges to read system catalog tables that you don't want them to read.
Details in the manual.
I have a view name customer and I want to restrict following SQL command
select * from customer;
I want to create a view where user must have where clause and only it is executable
select * from customer where address='ABC';
Use contexts.
create context where_condition using your_context_pkg;
Then use the context in the view:
create view customer_v as
select * from customer
where address = sys_context('where_condition', 'addreess')
You have to provide a PL/SQL package, named your_context_pkg, where the context value is set with dbms_session.set_context(...).
The way you put it, you'd recreate the view as
create or replace view customer as
select whatever
from bunch_of_tables
where address is not null --> add this
If you need this feature for security reasions, familiarize yourself with role based security (RBS).
Is there a way to find all user accounts in Oracle which have been created by me?
The SELECT * FROM ALL_USERS; returns all users in Oracle, but there seems to be no way of defining the 'owner' of the account (ORC_SYS would be nice) so I can add a clause like
'WHERE OWNER !+ 'ORC_SYS' or something.
Thanks in advance
KS
If its only the users created by oracle at install time you want to exclude you can properly do it filtering on user_id. Normally these users will have the lowest numbers:
Ajust the 35 to your installation.
Select * from dba_users where user_id > 35;
And if you are running 12c or above there is a column "Oracle_maintained" telling you if it is an oracle created user.
Select * from dba_users where oracle_maintained = 'N';
If you have access to dba_users and your Oracle's version is 12.1 and above, you can filter by oracle_maintained column.
Otherwise, there is no "official" way to distinguish between oracle internal users and your own.
There are some indirect ways, though:
Filter by all_users.created column. Mostly, internal users are created when the database is created, so your users will be after this date. You may find the database creation time in v$database.created .
Filter by all_users.user_id. As above, mostly, internal users are created when the database is created, so they get low user_id. There are some exceptions for several users like SYSBACKUP, SYSDG.
Both ways may produce incorrect results when internal users are created much later than the database creation - for example when an Oracle Option is reinstalled.
Should you try:
SELECT * FROM dba_users;
I need to create views depending on users on a oracle database
For that, using System I use the following querys:
CREATE OR REPLACE VIEW PROT_VIEW AS SELECT USER_ID, ORDER_DATE, ORDER_DESC
FROM PROT
WHERE USER_ID=USER;
the tables and the values of them are as follows:
CREATE TABLE PROT(
USER_ID VARCHAR2(10),
ORDER_DATE DATE,
ORDER_DESC VARCHAR2(60));
INSERT INTO PROT VALUES ('ADM',SYSDATE+4,'FOUR DAYS LATER');
INSERT INTO PROT VALUES ('ADM',SYSDATE+5,'FIVE DAYS LATER');
INSERT INTO PROT VALUES ('STUD1',SYSDATE+6,'SIX DAYS LATER');
INSERT INTO PROT VALUES ('STUD2',SYSDATE+7,'SEVEN DAYS LATER') ;
After this I have 3 different users (adm,stud1 and stud2) and when I log them on I should be getting 3 different results (one for each user) from each select I do (depending on the user logged).
The problem is, no matter what which user I have logged in (system,adm,stud1,stud2) I get empty tables.
I would like to know what i'm doing wrong and what can I do to solve this problem
Thank you in advance for anyone who's willing to help
update: i've been messing around and the problem is that i cant connect to those users. i've granted create session with system to those users and tried to connect to them but I'm stuck on system
Nice way to accomplish this task is to use public synonym in my opinion.
After creating your view (prot_view) on system schema, create a public synonym with the same name as view :
create or replace public synonym prot_view for prot_view;
and issue :
grant select on prot_view to public;
to be able to get desired result from every schema without prefixing with system schema name :
select * from prot_view;
"the problem is that i cant connect to those users"
user is a pseduo-column which returns the name of the account you're currently connected as. You're logged in as SYSTEM so that's the value of user, and that's why your view returns no rows. So, contrary to your question title, the view restriction is working.
Which means the the real question is, why can't you connect as those other users? You have SYSTEM so you have the necessary privileges to straighten out the accounts by changing the passwords to something you know or granting create session, or whatever.
The typical syntax for creating a db link is as follows:
create database link remote_db_link
connect to remote_user
identified by remote_password
using 'remote_db'
But I'd like my DB link owned by another account after it's created. Is there a way to do this?
The following does NOT work:
create database link anotheruser.remote_db_link
connect to remote_user
identified by remote_password
using 'remote_db'
Sathya is correct, in that the CREATE DATABASE LINK syntax does not allow creating a database link in another schema. HOWEVER...
WORKAROUND
It IS possible to create a database link in another user's schema, as long as anotheruser has CREATE DATABASE LINK privilege, and the user you are connected as has CREATE ANY PROCEDURE privilege.
Here's the workaround I use:
create procedure anotheruser."tmp_doit_200906121431"
is
begin
execute immediate '
create database link remote_db_link
connect to remote_user
identified by remote_password
using ''remote_db'' ';
end;
/
begin
anotheruser."tmp_doit_200906121431";
end;
/
drop procedure anotheruser."tmp_doit_200906121431"
/
Let's unwind that. First, I create a procedure in the anotherusers's schema; this procedure contains the CREATE DATABASE LINK statement that I want to run.
When the procedure is executed, it runs as the owner of the procedure, such that the CREATE DATABASE LINK statement is executed by anotheruser.
The name of the procedure is not important, except that I need to make sure that it doesn't conflict with any existing object name. I use lowercase letters (enclosing the procedure name in double quotes), using "tmp" to mark this object as "temporary", and using the current yyyymmddhh24miss as the part of the procedure name. (I usually run a query of DBA_OBJECTS to check that a matching object_name does not exist.)
For a "one-off" type admin function, this is a viable workaround. I prefer this to the other alternative: saving the anotheruser's password, changing the password, connecting as the user, and resetting anotheruser's password back to the saved.)
Restrictions on DBLinks - You cannot create a database link in another user's schema, and you cannot qualify dblink with the name of a schema.
AS a sys user you can view all db links in SYS.DBA_DB_LINKS view.
That view use link$ and user$ table.
You can create new dblink as usually and it show at link$ table. Then change owner (use id from user$). commit. Done.