如何使用a JDBCRealm来处理servlet中的用户身份验证和授权?我能找到的唯一例子是创建DataSource web.xml(例如使用shiro 1.2.1对数据库进行身份验证).
我并不想在我的源代码树的数据库凭据(原因很明显),并希望通过JNDI使用上下文定义数据源,因为我有我在每一个其他的servlet项目用于任何其它目的,所有其他RDBMS我已经开发.
如何配置Shiro 从JNDI JDBCRealm获取它DataSource?
目前我有一个Swing应用程序,我不想集成Apache Shiro,以便对某些角色进行身份验证和委派权限.我已经设法从我为测试创建的shiro.ini文件中读取用户,它看起来像这样:
[users]
admin = 123456, Administrator
[role]
Administrator = *:*:*
Run Code Online (Sandbox Code Playgroud)
然而,这仅仅是为了测试,现在我需要从数据库中读取许可证,所以我在数据库中存储了一个包含我需要的信息的表,它看起来像这样:
users (id,password,username)
userRoles (userId, role)
rolePermission (permissionID,permission,roleID)
Run Code Online (Sandbox Code Playgroud)
我一直在尝试理解使用JDBC领域的教程,但是他们使用Web应用程序或特殊框架来管理他们与Apache Derby或BoneCP之类的数据库的连接,他们更加困惑我这些例子.
所以我要问的是,如果我想使用JDBC领域(使用Oracle数据库)以及shiro.ini需要什么类,我需要配置shiro.ini文件.任何例子或解释将不胜感激!
我创建了基于Jersey的Web服务(通过Netbeans自动生成).
我还创建了一个用户名"testClient",密码为"secret",并创建了用户组"Users",并使用了glassfish 3.0.1管理控制台使用文件Realm.
我还相应地映射了web.xml和sun-web.xml.
我的网络服务已成功保护; 当我访问该网站时,我收到安全警告,然后我提示用户名和密码来访问该网站的任何内容.通过Web浏览器访问它时工作正常.
现在我已经编写了一个基于jersey的简单客户端,并试图访问第一个项目提供的Web服务; 客户端代码在这里
自动生成Jersey客户端代码
public class JerseyClient {
private WebResource webResource;
private Client client;
private static final String BASE_URI = "https://localhost:9028/testsecurity2/resources";
public JerseyClient() {
com.sun.jersey.api.client.config.ClientConfig config = new com.sun.jersey.api.client.config.DefaultClientConfig(); // SSL configuration
// SSL configuration
config.getProperties().put(com.sun.jersey.client.urlconnection.HTTPSProperties.PROPERTY_HTTPS_PROPERTIES, new com.sun.jersey.client.urlconnection.HTTPSProperties(getHostnameVerifier(), getSSLContext()));
client = Client.create(config);
webResource = client.resource(BASE_URI).path("manufacturers");
}
public <T> T get_XML(Class<T> responseType) throws UniformInterfaceException {
return webResource.accept(javax.ws.rs.core.MediaType.APPLICATION_XML).get(responseType);
}
public <T> T get_JSON(Class<T> responseType) throws UniformInterfaceException {
return webResource.accept(javax.ws.rs.core.MediaType.APPLICATION_JSON).get(responseType);
}
public void close() {
client.destroy();
}
public …Run Code Online (Sandbox Code Playgroud) 我在glassfish v3.0.1 b22中使用jdbcRealm来保证安全性.它被设置为使用我的数据库中的USER表进行身份验证,方法是访问以下博客:http://blogs.oracle.com/foo/entry/mort_learns_jdbc_realm_authentication.如果我将摘要算法保留为纯文本,我的工作正常.但是,当我尝试使用SHA-256进行摘要算法时,它会停止工作.我所做的是在Glassfish中指定 - 安全 - 领域 - jdbcRealm - 我想要SHA-256的摘要(我只是在摘要字段中键入SHA-256).然后我写了一个简单的Java程序,将密码文本转换为SHA-256哈希.然后我将该哈希粘贴到数据库中的密码字段中.顺便说一句,密码字段是类型varchar(30).我不能再登录了.有一点我注意到我的简单Java程序每次为同一文本字段生成不同的哈希值.
下面是我简单的java程序:
MessageDigest md = MessageDigest.getInstance("SHA-256");
String text = "admin";
md.update(text.getBytes("UTF-8"));
byte[] digest = md.digest();
System.out.println(digest.toString());
Run Code Online (Sandbox Code Playgroud) 我正在尝试使用Shiro验证在Tomcat 6中运行的servlet.
我有以下shiro.ini文件:
[main]
ps = org.apache.shiro.authc.credential.DefaultPasswordService
pm = org.apache.shiro.authc.credential.PasswordMatcher
pm.passwordService = $ps
aa = org.apache.shiro.authc.credential.AllowAllCredentialsMatcher
sm = org.apache.shiro.authc.credential.SimpleCredentialsMatcher
jof = org.apache.shiro.jndi.JndiObjectFactory
jof.resourceName = jdbc/UserDB
jof.requiredType = javax.sql.DataSource
jof.resourceRef = true
realm = org.apache.shiro.realm.jdbc.JdbcRealm
realm.permissionsLookupEnabled = true
realm.credentialsMatcher = $pm
; Note factories are automatically invoked via getInstance(),
; see org.apache.shiro.authc.config.ReflectionBuilder::resolveReference
realm.dataSource = $jof
securityManager.realms = $realm
[urls]
/rest/** = authcBasic
/prot/** = authcBasic
Run Code Online (Sandbox Code Playgroud)
以下在我的数据库中:
mysql> select * from users;
+----------+------------------+----------+----------------------------------------------+--------------------------+
| username | email | verified | password | …Run Code Online (Sandbox Code Playgroud) 我正在尝试使用GlassFish v3.1.1 Build 12和JSF 2.1设置容器管理的安全性.由于某种原因我一直收到以下异常,我无法登录.
WARNING: WEB9102: Web Login Failed: com.sun.enterprise.security.auth.login.common.LoginException: Login failed: Security Exception
WARNING: Exception
com.sun.enterprise.security.auth.login.common.LoginException: Login failed: Security Exception
at com.sun.enterprise.security.auth.login.LoginContextDriver.doPasswordLogin(LoginContextDriver.java:394)
at com.sun.enterprise.security.auth.login.LoginContextDriver.login(LoginContextDriver.java:240)
at com.sun.enterprise.security.auth.login.LoginContextDriver.login(LoginContextDriver.java:153)
at com.sun.web.security.RealmAdapter.authenticate(RealmAdapter.java:512)
at com.sun.web.security.RealmAdapter.authenticate(RealmAdapter.java:453)
at org.apache.catalina.connector.Request.login(Request.java:1932)
at org.apache.catalina.connector.Request.login(Request.java:1895)
at org.apache.catalina.connector.RequestFacade.login(RequestFacade.java:1146)
at com.perpro.controller.MemberBean.doNavigation(MemberBean.java:354)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at com.sun.el.parser.AstValue.invoke(AstValue.java:234)
at com.sun.el.MethodExpressionImpl.invoke(MethodExpressionImpl.java:297)
at org.jboss.weld.util.el.ForwardingMethodExpression.invoke(ForwardingMethodExpression.java:43)
at org.jboss.weld.el.WeldMethodExpression.invoke(WeldMethodExpression.java:56)
at com.sun.faces.facelets.el.TagMethodExpression.invoke(TagMethodExpression.java:105)
at javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:88)
at com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:102)
at javax.faces.component.UICommand.broadcast(UICommand.java:315)
at javax.faces.component.UIViewRoot.broadcastEvents(UIViewRoot.java:794)
at javax.faces.component.UIViewRoot.processApplication(UIViewRoot.java:1259)
at com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:81)
at com.sun.faces.lifecycle.Phase.doPhase(Phase.java:101)
at com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:118)
at javax.faces.webapp.FacesServlet.service(FacesServlet.java:593)
at org.apache.catalina.core.StandardWrapper.service(StandardWrapper.java:1539)
at …Run Code Online (Sandbox Code Playgroud) 我在Glassfish 3.1.1中配置了一个新的jdbcRealm并启用了FINEST日志记录,当我尝试使用用户名和密码登录时,我得到以下内容.它抱怨我的web应用程序映射到的领域是一个fileRealm,当它真的是一个jdbcRealm.关于为什么Glassfish认为它是fileRealm的任何想法?
FINE: [Web-Security] Setting Policy Context ID: old = null ctxID = PerPro/PerPro
FINE: [Web-Security] hasUserDataPermission perm: (javax.security.jacc.WebUserDataPermission /index.jsf POST)
FINE: [Web-Security] hasUserDataPermission isGranted: true
FINEST: Processing login with credentials of type: class com.sun.enterprise.security.auth.login.common.PasswordCredential
FINE: Logging in user [admin] into realm: file using JAAS module: fileRealm
FINE: Login module initialized: class com.sun.enterprise.security.auth.login.FileLoginModule
FINE: No such user: [admin]
FINE: JAAS authentication aborted.
FINEST: doPasswordLogin fails
javax.security.auth.login.LoginException: Failed file login for admin.
at com.sun.enterprise.security.auth.login.FileLoginModule.authenticate(FileLoginModule.java:84)
at com.sun.enterprise.security.auth.login.PasswordLoginModule.authenticateUser(PasswordLoginModule.java:117)
at com.sun.appserv.security.AppservPasswordLoginModule.login(AppservPasswordLoginModule.java:148)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) …Run Code Online (Sandbox Code Playgroud) 我有以下数据库模式(MySQL):

我的登录是一个基于表单的身份验证系统,我正在尝试创建一个jdbc领域.

我的web.xml:
<login-config>
<auth-method>FORM</auth-method>
<realm-name>emdJDBCRealm</realm-name>
<form-login-config>
<form-login-page>/index.jsp</form-login-page>
<form-error-page>/WEB-INF/loginerror.jsp</form-error-page>
</form-login-config>
</login-config>
<security-constraint>
<web-resource-collection>
<web-resource-name>Login Page</web-resource-name>
<url-pattern>/*</url-pattern>
</web-resource-collection>
<auth-constraint>
<role-name>adm</role-name>
<role-name>usr</role-name>
</auth-constraint>
<user-data-constraint>
<transport-guarantee>CONFIDENTIAL</transport-guarantee>
</user-data-constraint>
</security-constraint>
<security-role>
<description/>
<role-name>usr</role-name>
</security-role>
<security-role>
<description/>
<role-name>adm</role-name>
</security-role>
Run Code Online (Sandbox Code Playgroud)
和sun-web.xml中的映射:
<security-role-mapping>
<role-name>adm</role-name>
<group-name>adm</group-name>
</security-role-mapping>
<security-role-mapping>
<role-name>usr</role-name>
<group-name>usr</group-name>
</security-role-mapping>
Run Code Online (Sandbox Code Playgroud)
我不知道为什么,但它不适合我,我得到以下内容:
FINE: Cannot load group
com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException: Unknown column 'group_name' in 'field list'
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:39)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:27)
at java.lang.reflect.Constructor.newInstance(Constructor.java:513)
at com.mysql.jdbc.Util.handleNewInstance(Util.java:407)
at com.mysql.jdbc.Util.getInstance(Util.java:382)
at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:1052)
at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3603)
at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3535)
at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:1989)
at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2150)
at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2626) …Run Code Online (Sandbox Code Playgroud) 我们目前正在使用tomcat 5.5,并希望在我们的JDBCRealm身份验证中添加一个salt.我想知道是否有任何现有的类或我们是否需要扩展JDBCRealm并编写我们自己的身份验证类?
我们的server.xml中有以下内容
<Realm className="org.apache.catalina.realm.JDBCRealm" ...more stuff… />
Run Code Online (Sandbox Code Playgroud)
但它看起来并不像这个类需要盐.
我最近将Glassfish从3.1.2更新到4.0,并希望在我的应用程序中使用我之前使用的基于FORM身份验证的JDBCRealm.密码在数据库中使用SHA-256进行哈希处理(这是默认的摘要算法选项).
该领域具有在此Glassfish版本中必需的属性:密码加密算法.相当令人难以置信的是,官方的Glassfish文档说它是可选的,并且输入字段下的注释表示将它留空是一种风险,但是你不能将它留空,因为它是强制性的.
无论我在此属性中设置什么,我都无法登录之前正在运行的应用程序.(对于新注册的用户和老用户都是如此.)我谷歌搜索了好几天但找不到这个字段的选项.有什么选择?
另外,我正在使用Glassfish和MySQL.Glassfish是否将加密的散列密码发送到数据库,或者它只是MySQL的一些指令,用于存储带有这种加密的散列密码?
这个问题对我有所帮助,但没有解决我的问题.
更新:实际上,我不使用经典的基于FORM的身份验证,而是使用程序化登录的自定义JSF表单HttpServletRequest#login(),但我不认为这个问题很重要.