Tuesday, 8 April 2014

Java security for Oracle from 8.1.6


Beginning with 8.1.6, Oracle’s JVM offered support for Java 2 security, in which permissions
are granted on a class-by-class basis. This is a much more sophisticated and
fine-grained approach to security. This section offers some examples to give you a sense
of the kind of security-related code you could write (check Oracle’s manuals for more
details and examples).
Generally, you will use the DBMS_JAVA.GRANT_PERMISSION procedure to grant
the appropriate permissions. Here is an example of calling that program to give the
BATCH schema permission to read and write the lastorder.log file:

 

/* Must be connected as a dba */
BEGIN
DBMS_JAVA.grant_permission(
grantee => 'BATCH',
permission_type => 'java.io.FilePermission',
permission_name => '/apps/OE/lastorder.log',
permission_action => 'read,write');
END;
/
COMMIT;

 

When making such a call, be sure to uppercase the grantee; otherwise, Oracle won’t
be able to locate the account name.
Also note the COMMIT. It turns out that this DBMS_JAVA call is just writing permission
data to a table in Oracle’s data dictionary, but it does not commit automatically.
And, by the way, you can query permission data through the views
USER_JAVA_POLICY and DBA_JAVA_POLICY.
Here is a sequence of commands that first grants permission to access files in a directory,
and then restricts permissions on a particular file:
 

BEGIN
/* First, grant read and write to everyone */
DBMS_JAVA.grant_permission(
'PUBLIC',
'java.io.FilePermission',
'/shared/*',
'read,write');
/* Use the "restrict" built-in to revoke read & write
| permission on one particular file from everyone
*/
DBMS_JAVA.restrict_permission(
'PUBLIC',
'java.io.FilePermission',
'/shared/secretfile',
'read,write');
/* Now override the restriction so that one user can read and write
| that file.
*/
DBMS_JAVA.grant_permission(
'BOB',
'java.io.FilePermission',
'/shared/secretfile',
'read,write');
COMMIT;
END;
 

Here are the predefined permissions that Oracle offers:
 

java.util.PropertyPermission
java.io.SerializablePermission
java.io.FilePermission
java.net.NetPermission
java.net.SocketPermission
java.lang.RuntimePermission
java.lang.reflect.ReflectPermission
java.security.SecurityPermission
oracle.aurora.rdbms.security.PolicyTablePermission
oracle.aurora.security.JServerPermission

 

Oracle also supports the Java mechanisms for creating your own permissions; check
Oracle’s Java Developer’s Guide for details.
 

A Simple Demonstration
Before diving into the details, let’s walk through all the steps needed to access Java from
within PL/SQL. In the process, I’ll introduce the various pieces of technology you need
to get the job done.
Say that I need to be able to delete a file from within PL/SQL. Prior to Oracle8i Database,
I had the following options.
• In Oracle7 Database (7.3) (and above), I could send a message to a database pipe
and then have a C listener program grab the message (“Delete file X”) and do all
the work.
• In Oracle8 Database and later, I could set up a library that pointed to a C DLL or
shared library, and then from within PL/SQL, call a program in that library to delete
the file.
The pipe technique is handy, but it is a clumsy workaround. The external procedure
implementation in Oracle8 Database is a better solution, but it is also less than straightforward,
especially if you don’t know the C language. So the Java solution looks as if
it might be the best one all around. Although some basic knowledge of Java is required,
you don’t need the same level of skill that would be required to write the equivalent
code in C. Java comes with prebuilt (foundation) classes that offer clean, easy-to-use
APIs to a wide array of functionality, including file I/O.
Here are the steps that I will perform in this demonstration:
 

1. Identify the Java functionality I need to access.
2. Build a class of my own to make the underlying Java feature callable through
PL/SQL.
3. Compile the class and load it into the database.
4. Build a PL/SQL program to call the class method I created.
5. Delete files from within PL/SQL.

 

Finding the Java Functionality
A while back, my O’Reilly editor, Deborah Russell, was kind enough to send me a
whole bunch of their Java books, so I grabbed the big, fat Java Fundamental Classes
Reference, by Mark Grand and Jonathan Knudsen, and looked up “File” in the index
(sure, I could use online documentation, but I like books). The entry for “File class”
caught my eye, and I hurried to the correct page.
There I found information about the class named java.io.File, namely, that it “provides
a set of methods to obtain information about files and directories.” And it doesn’t just
let you obtain information; it also contains methods (procedures and functions) to
delete and rename files, make directories, and so on. I had come to the right place!
Here is a portion of the API offered by the File class:
 

public class java.io.File {
public boolean delete();
public boolean mkdir ();
}
 

In other words, I will call a Boolean function in Java to delete a file. If the file is deleted,
the function returns TRUE; otherwise, it returns FALSE.

 

Building a Custom Java Class
Now, you might be asking yourself why I had to build my own Java class on top of the
File class. Why can’t I just call that function directly inside my PL/SQL wrapper? There
are two reasons:
• A Java class method is typically executed for a specific object instantiated from the
class. In PL/SQL I cannot instantiate a Java object and then call the method against
that object; in other words, PL/SQL only allows the calling of static methods.

• Even though Java and PL/SQL both have Boolean datatypes (Java even offers a
Boolean primitive and a Boolean class), they do not map to each other. I cannot
pass a Boolean from Java directly to a PL/SQL Boolean.
As a direct consequence, I need to build my own class that will:
• Instantiate an object from the File class
• Execute the delete method against that object
• Return a value that PL/SQL interprets properly
Here is the very simple class I wrote to take advantage of the File.delete method:

 

/* File on web: JDelete.java */
import java.io.File;
public class JDelete {
public static int delete (String fileName) {
File myFile = new File (fileName);
boolean retval = myFile.delete();
if (retval) return 1; else return 0;
}
}

 

Figure 27-2 explains each of the steps in this code, but the main effect is clear: the
JDelete.delete method simply instantiates a dummy File object for the specified filename
so that I can call the delete method for that file. By declaring my method to be
static, I make that method available without the need to instantiate an object. Static
methods are associated with the class, not with the individual instances of the objects
of that class.
The JDelete class above highlights a number of differences between Java and PL/SQL
that you should keep in mind:
• There are no BEGIN and END statements in Java for blocks, loops, or conditional
statements. Instead, you use curly braces to delimit the block.
• Java is case-sensitive; “if ” is definitely not the same thing as “IF”.
• The assignment operator is a plain equals sign (=) rather than the compound symbol
used in PL/SQL (:=).
• When you call a method that does not have any arguments (such as the delete
method of the File class), you still must open and close the parentheses. Otherwise,
the Java compiler will try to interpret the method as a class member or data
structure.
Hey, that was easy! Of course, you didn’t watch me fumble around with Java for a day,
getting over the nuisance of minor syntax errors, the agony of a case-sensitive language,
and the confusion setting the CLASSPATH. I’ll leave all that to your imagination—and
your own day of fumbling!




Figure 27-2. A simple Java class used to delete a file

                                 
                                    "News powered by"




No comments:

Post a Comment

About Me

Popular Posts

Designed By Seo Blogger Templates