WebLogicServer的JAAS编写与安全领域定制
立即解锁
发布时间: 2025-08-24 00:58:30 阅读量: 1 订阅数: 7 

# WebLogic Server的JAAS编写与安全领域定制
## 1. WebLogic Server的JAAS扩展
JAAS(Java Authentication and Authorization Service)示例通常用于JAAS v1.0包,而WebLogic Server对其进行了扩展,以便在WebLogic认证和安全领域中使用。与传统的JAAS实现相比,WebLogic Server的认证登录使用URL来访问服务器,而不是通过策略文件,并且调用WebLogic Server的Authenticate类来验证用户。
### 1.1 登录函数示例
以下是一个登录函数的示例代码:
```java
/**
* Authenticate the user by username and password passed in
*
* @return true in all cases
*
* @exception LoginException if this LoginModule
* is unable to perform the authentication.
*/
public boolean login() throws LoginException {
// Verify that the client supplied a callback handler
if (callbackHandler == null) {
throw new LoginException("No CallbackHandler Specified");
}
// Populate callback list
Callback[] callbacks = new Callback[2];
callbacks[0] = new NameCallback("username: ");
callbacks[1] = new PasswordCallback("password: ", false);
try {
// Prompt for username and password
callbackHandler.handle(callbacks);
// Retrieve username
username = ((NameCallback) callbacks[0]).getName();
// Retrieve password, converting from char[] to String
char[] charPassword = ((PasswordCallback) callbacks[1]).getPassword();
if (charPassword == null) {
// Treat a NULL password as an empty password, not NULL
charPassword = new char[0];
}
password = new String(charPassword);
} catch (IOException ioe) {
throw new LoginException(ioe.toString());
} catch (UnsupportedCallbackException uce) {
throw new LoginException("Error: Callback "
+ uce.getCallback().toString() + " Not Available");
}
// Populate weblogic environment and authenticate
/* WebLogic Only */
Environment env = new Environment();
env.setProviderUrl(url);
env.setSecurityPrincipal(username);
env.setSecurityCredentials(password);
try {
// Authenticate user credentials, populating Subject
/* WebLogic Specific */
Authenticate.authenticate(env, subject);
/* Non−WebLogic Function for Login */
//authenticate(username, password);
} catch(RemoteException re) {
System.err.println("Error: Remote Exception on authenticate, " +
re.getMessage());
throw new LoginException(re.toString());
} catch(IOException ioe) {
System.err.println("Error: IO Exception on authenticate, " +
ioe.getMessage());
throw new LoginException(ioe.toString());
} catch (LoginException le) {
System.err.println("Error: Login Exception on authenticate, "
+ le.getMessage());
throw new LoginException(le.toString());
}
// Successfully authenticated subject with supplied info
succeeded = true;
return succeeded;
}
```
### 1.2 替代策略文件
通过重写Configuration对象的getAppConfigurationEntry()函数,可以使用URL替代策略文件。以下是一个示例配置类:
```java
package com.hungryminds.wljaas;
/*
* Class SampleAction
*/
import java.util.Hashtable;
import javax.security.auth.login.Configuration;
import javax.security.auth.login.AppConfigurationEntry;
import java.io.File;
import java.io.FileReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
/**
* Sample configuration class for JAAS user authentication.
*/
public class ConfigFile extends Configuration
{
String configFileName = null;
/**
*
* Create a new Configuration object.
*/
public ConfigFile()
{
}
/**
* Retrieve an entry from the Configuration object
* using an application name as an index.
*/
public AppConfigurationEntry[] getAppConfigurationEntry(
String applicationName)
{
AppConfigurationEntry[] list = new AppConfigurationEntry[1];
AppConfigurationEntry entry = null;
/* Get the spcified configuration file */
configFileName = System.getProperty("weblogic.security.jaas.Policy");
try
{
FileReader fr = new FileReader(configFileName);
BufferedReader reader = new BufferedReader(fr);
String line;
line = reader.readLine();
while(line != null)
{
// Skip lines until the line starting with a ‘{‘
if(line.length() == 0 || line.charAt(0) != ‘{‘)
{
line = reader.readLine();
continue;
}
/* Read following line which contains the LoginModule configured */
line = reader.readLine();
int i;
for(i = 0; i < line.length(); i++)
{
char c = line.charAt(i);
if(c != ‘ ‘)
break;
}
int sep = line.indexOf(‘ ‘, i);
String LMName = line.substring(0, sep).trim();
String LMFlag = line.substring(sep + 1,
line.indexOf(‘ ‘, sep + 1));
if(LMFlag.equalsIgnoreCase("OPTIONAL")) {
entry = new AppConfigurationEntry(LMName,
AppConfigurationEntry.LoginModuleControlFlag.OPTIONAL,
new Hashtable());
list[0] = entry;
}
else if(LMFlag.equalsIgnoreCase("REQUIRED"))
{
entry = new AppConfigurationEntry(LMName,
AppConfigurationEntry.LoginModuleControlFlag.REQUIRED,
new Hashtable());
list[0] = entry;
}
else if(LMFlag.equalsIgnoreCase("REQUISITE"))
{
entry = new AppConfigurationEntry(LMName,
AppConfigurationEntry.LoginModuleControlFlag.REQUISITE,
new Hashtable());
list[0] = entry;
}
else if(LMFlag.equalsIgnoreCase("SUFFICIENT"))
{
entry = new AppConfigurationEntry(LMName,
AppConfigurationEntry.LoginModuleControlFlag.SUFFICIENT,
new Hashtable());
list[0] = entry;
}
else
{
throw new IllegalArgumentException("Invalid controlFlag");
}
line = reader.readLine();
}
reader.close();
}
catch(java.io.FileNotFoundException ioe)
{
System.out.println(ioe.toString());
}
catch(java.io.IOException ioe)
{
System.out.println(ioe.toString());
}
return list;
}
/**
* Refresh and reload the Configuration object by reading
* all of the login configurations again.
*/
public void refresh()
{
// No Implementation
}
}
```
### 1.3 用户登录与测试
用户登录WebLogic Server时,需要在authenticate函数中输入有效的用户名和密码。示例代码中硬编码的用户名和密码如下:
```java
private final static String USERNAME = "rich";
private final static String PASSWORD = "richpass";
```
以下是一个测试认证和JAAS客户端访问WebLogic Server的示例类:
```java
package com.hungryminds.wljaas;
import java.security.PrivilegedAction;
import javax.naming.Context;
import javax.naming.InitialContext;
import java.util.Hashtable;
import javax.naming.*;
public class SampleAction implements PrivilegedAction {
public Object run() {
Object obj = null;
Context ctx = null;
String url = null;
try {
// Retrieve WLS server URL string
url = System.getProperty("weblogic.security.jaas.ServerURL");
} catch (NullPointerException npe) {
System.err.println("Error: ServerURL Not Specified");
return null;
} catch (IllegalArgumentException iae) {
System.err.println("Error: ServerURL Not Specified");
return null;
} catch (SecurityException se) {
System.err.println(
"Error: Security Exception on accessing ServerURL Specification");
return null;
}
// Populate environment
Hashtable env = new Hashtable();
env.put(Context.INITIAL_CONTEXT_FACTORY,
"weblogic.jndi.WLInitialContextFactory");
env.put(Context.PROVIDER_URL, url);
try {
// Create InitialContext
ctx = new InitialContext(env);
printBindingList("", ctx.listBindings(""));
printNameList("", ctx.list(""));
/**
* Execute target EJB Frobable.frob() method. (This is left over from
* the WLS example − it is intended to show that there is differences
* and similarities to show that the same code slightly modified
* works in both instances.)
*/
System.out.println("JNDI Lists successfully");
} catch (Throwable t) {
t.printStackTrace();
System.out.println("Failed to lists JNDI");
} finally {
try {
// Close InitialContext
ctx.close();
} catch (Exception e) {
// Deal with any failures
}
}
return obj;
}
void printNameList(String msg, NamingEnumeration nl) {
System.out.println(msg);
if (nl == null) {
System.out.println("No items in name list");
} else {
try {
while (nl.hasMore()) {
System.out.println(nl.next());
}
} catch (NamingException e) {
e.printStackTrace();
}
}
}
void printBindingList(String msg, NamingEnumeration bl) {
System.out.println(msg);
if (bl == null) {
System.out.println("No items in binding list");
} else {
try {
while (bl.hasMore()) {
Binding b = (Binding) bl.next();
System.out.println(b.getName() + "(" + b.getObject() + ")");
}
} catch (NamingException e) {
e.printStackTrace();
}
}
}
}
```
### 1.4 JNDI权限问题
默认情况下,每个用户都有列出和修改JNDI条目的权限,这可能会带来安全风险。一些JNDI服务应该只对系统用户开放。
## 2. 授权与安全领域
WebLogic Server有自己的安全领域类型,并使用自己的ACL(Access Control List)接口进行通信。weblogic.security.acl.Security类仅在服务器端代码中可用,需要访问客户端类无法访问的安全领域。
### 2.1 Security类的使用
Security类有许多功能,其中Security.getRealm()是一个静态函数,返回BasicRealm的实例。BasicRealm提供了对安全领域的最小接口,可列出领域管理的所有实例,并具有创建和销毁实例的能力。访问BasicRealm后,可以使用getUser()函数从安全领域中检索用户,使用getPermission()函数检索权限。
### 2.2 权限检查方法
Security.hasPermission()和Security.checkPermission()是Security类中定义的静态函数,用于测试用户是否具有访问资源的正确权限。两者的区别在于,Security.checkPermission()在用户没有权限时会抛出java.lang.SecurityException,而Security.hasPermission()会返回false。
## 3. 构建自定义RDBMS安全领域
WebLogic允许创建自定义安全领域,下面以RDBMS为例进行说明。
### 3.1 数据存储定义
WebLogic Server 6.1附带了Cloudscape数据库的评估版本,这是一个纯Java的关系型数据库管理系统(RDBMS)。使用Cloudscape与WebLogic Server时,需要将Cloudscape库cloudscape.jar添加到WebLogic Server的CLASSPATH中,并设置cloudscape.system.home Java系统属性为包含C
0
0
复制全文
相关推荐









