【发布时间】:2014-08-06 03:06:51
【问题描述】:
我是 Java EE 的新手,刚开始使用 tomcat。我正在使用 PrimeFaces 开发一个小型任务应用程序。
应用程序有一个主页和管理区域,受 web.xml 文件保护。当我根据http://docs.oracle.com/cd/E19159-01/819-3669/bncby/index.html 此处发布的指南开发登录页面时。尽管我已正确配置领域,但我无法登录。
我在JSP web application form based authentication in tomcat 上阅读了这篇文章,这正是我遇到的问题。但我没有使用 Eclipse。
这些是我的编码和 XML 配置文件。
login.jsp 页面
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Log In</title>
</head>
<body>
<form method="post" action="j_security_check">
<p>Username</p>
<input type="text" name="j_username" />
<p>Password</p>
<input type="password" name="j_password" />
<p></p>
<input type="submit" value="Submit" /> <input type="reset"
value="reset" />
</form>
</body>
</html>
web.xml 文件
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd" id="WebApp_ID" version="3.0">
<display-name>ToDoApplication</display-name>
<welcome-file-list>
<welcome-file>index.xhtml</welcome-file>
</welcome-file-list>
<!-- JSF Mapping -->
<servlet>
<servlet-name>Faces Servlet</servlet-name>
<servlet-class>javax.faces.webapp.FacesServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>Faces Servlet</servlet-name>
<url-pattern>/faces/*</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>Faces Servlet</servlet-name>
<url-pattern>*.jsf</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>Faces Servlet</servlet-name>
<url-pattern>*.faces</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>Faces Servlet</servlet-name>
<url-pattern>*.xhtml</url-pattern>
</servlet-mapping>
<security-constraint>
<display-name>Main Login Auth</display-name>
<web-resource-collection>
<web-resource-name>Restricted Access</web-resource-name>
<url-pattern>/admin/*</url-pattern>
</web-resource-collection>
<auth-constraint>
<role-name>admin</role-name>
</auth-constraint>
<user-data-constraint>
<transport-guarantee>NONE</transport-guarantee>
</user-data-constraint>
</security-constraint>
<security-role>
<role-name>management</role-name>
</security-role>
<security-role>
<role-name>sales</role-name>
</security-role>
<security-role>
<role-name>admin</role-name>
</security-role>
<login-config>
<auth-method>FORM</auth-method>
<form-login-config>
<form-login-page>/login.jsp</form-login-page>
<form-error-page>/error.jsp</form-error-page>
</form-login-config>
</login-config>
</web-app>
这是我在 tomcat/conf 文件夹中的 server.xml。
<!-- Note: A "Server" is not itself a "Container", so you may not
define subcomponents such as "Valves" at this level.
Documentation at /docs/config/server.html
-->
<Server port="8005" shutdown="SHUTDOWN">
<!-- Security listener. Documentation at /docs/config/listeners.html
<Listener className="org.apache.catalina.security.SecurityListener" />
-->
<!--APR library loader. Documentation at /docs/apr.html -->
<Listener className="org.apache.catalina.core.AprLifecycleListener" SSLEngine="on" />
<!--Initialize Jasper prior to webapps are loaded. Documentation at /docs/jasper-howto.html -->
<Listener className="org.apache.catalina.core.JasperListener" />
<!-- Prevent memory leaks due to use of particular java/javax APIs-->
<Listener className="org.apache.catalina.core.JreMemoryLeakPreventionListener" />
<Listener className="org.apache.catalina.mbeans.GlobalResourcesLifecycleListener" />
<Listener className="org.apache.catalina.core.ThreadLocalLeakPreventionListener" />
<!-- Global JNDI resources
Documentation at /docs/jndi-resources-howto.html
-->
<GlobalNamingResources>
<!-- Editable user database that can also be used by
UserDatabaseRealm to authenticate users
-->
<Resource name="UserDatabase" auth="Container"
type="org.apache.catalina.UserDatabase"
description="User database that can be updated and saved"
factory="org.apache.catalina.users.MemoryUserDatabaseFactory"
pathname="conf/tomcat-users.xml" />
</GlobalNamingResources>
<!-- A "Service" is a collection of one or more "Connectors" that share
a single "Container" Note: A "Service" is not itself a "Container",
so you may not define subcomponents such as "Valves" at this level.
Documentation at /docs/config/service.html
-->
<Service name="Catalina">
<!--The connectors can use a shared executor, you can define one or more named thread pools-->
<!--
<Executor name="tomcatThreadPool" namePrefix="catalina-exec-"
maxThreads="150" minSpareThreads="4"/>
-->
<!-- A "Connector" represents an endpoint by which requests are received
and responses are returned. Documentation at :
Java HTTP Connector: /docs/config/http.html (blocking & non-blocking)
Java AJP Connector: /docs/config/ajp.html
APR (HTTP/AJP) Connector: /docs/apr.html
Define a non-SSL HTTP/1.1 Connector on port 8081
-->
<Connector port="8081" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" />
<!-- A "Connector" using the shared thread pool-->
<!--
<Connector executor="tomcatThreadPool"
port="8080" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" />
-->
<!-- Define a SSL HTTP/1.1 Connector on port 8443
This connector uses the BIO implementation that requires the JSSE
style configuration. When using the APR/native implementation, the
OpenSSL style configuration is required as described in the APR/native
documentation -->
<!--
<Connector port="8443" protocol="org.apache.coyote.http11.Http11Protocol"
maxThreads="150" SSLEnabled="true" scheme="https" secure="true"
clientAuth="false" sslProtocol="TLS" />
-->
<!-- Define an AJP 1.3 Connector on port 8009 -->
<Connector port="8009" protocol="AJP/1.3" redirectPort="8443" />
<!-- An Engine represents the entry point (within Catalina) that processes
every request. The Engine implementation for Tomcat stand alone
analyzes the HTTP headers included with the request, and passes them
on to the appropriate Host (virtual host).
Documentation at /docs/config/engine.html -->
<!-- You should set jvmRoute to support load-balancing via AJP ie :
<Engine name="Catalina" defaultHost="localhost" jvmRoute="jvm1">
-->
<Engine name="Catalina" defaultHost="localhost">
<!--For clustering, please take a look at documentation at:
/docs/cluster-howto.html (simple how to)
/docs/config/cluster.html (reference documentation) -->
<!--
<Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster"/>
-->
<!-- Use the LockOutRealm to prevent attempts to guess user passwords
via a brute-force attack -->
<Realm className="org.apache.catalina.realm.LockOutRealm">
<!-- This Realm uses the UserDatabase configured in the global JNDI
resources under the key "UserDatabase". Any edits
that are performed against this UserDatabase are immediately
available for use by the Realm. -->
<Realm className="org.apache.catalina.realm.UserDatabaseRealm"
resourceName="UserDatabase"/>
</Realm>
<!-- Edited by Me while adding support to JDBC database configuration -->
<context path="/ToDoApplication" privileged="true" reloadable="true" cookies="true" debug="true">
<Realm className="org.apache.catalina.realm.JDBCRealm"
driverName="com.mysql.jdbc.Driver"
connectionURL="jdbc:mysql://localhost/todo?user=tomcat&password=tomcat"
userTable="users" userNameCol="username" userCredCol="password"
userRolesTable="user_roles" roleNameCol="rolename"/>
</context>
<!-- Editing finished -->
<Host name="localhost" appBase="webapps"
unpackWARs="true" autoDeploy="true">
<!-- SingleSignOn valve, share authentication between web applications
Documentation at: /docs/config/valve.html -->
<!--
<Valve className="org.apache.catalina.authenticator.SingleSignOn" />
-->
<!-- Access log processes all example.
Documentation at: /docs/config/valve.html
Note: The pattern used is equivalent to using pattern="common" -->
<Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs"
prefix="localhost_access_log." suffix=".txt"
pattern="%h %l %u %t "%r" %s %b" />
</Host>
</Engine>
</Service>
</Server>
这就是我准备数据库表的方式,数据库称为'todo'。
mysql> SELECT * FROM users;
+----------+----------+
| username | password |
+----------+----------+
| lal | lal |
| lala | lala |
| mad | mada |
| nalaka | nalaka |
+----------+----------+
4 rows in set (0.00 sec)
mysql> SELECT * FROM user_roles;
+----------+------------+
| username | rolename |
+----------+------------+
| lal | sales |
| lala | management |
| lala | sales |
| mad | admin |
| nalaka | sales |
+----------+------------+
5 rows in set (0.00 sec)
我必须使用用户 mad 登录,因为在 web.xml 文件中我已将角色指定为 admin 以登录到管理区域。 当我分别使用用户名和密码作为 mad 和 mada 时,我被重定向到错误页面。并且 URL 像这样附加了 j_security_check。
http://localhost:8081/ToDoApplication/admin/j_security_check
数据库用户 tomcat 拥有 todo 数据库的 SELECT 权限。 tomcat 指南中提到,由于 tomcat 服务器不会写入数据库,因此用户必须至少具有读取权限。
【问题讨论】:
-
Facesservlet 配置中没有 *.jsp,但如果您要使用 FacesServlet,它需要是 h:form/h:body。使用 JPA 会更容易,但是当您使用 sql 时 - 您可以显示您的控制器登录方法吗?
-
@VeenarM 我将 login.jsp 更改为 login.xhtml,仍然无法正常工作。关于 h 前缀,页面正确呈现!。
-
@VeenarM 我曾想过使用 JPA,但想尝试一下 tomcat 的内置身份验证。登录的控制器方法是标准的 j_security_check。我没有明确指定一个控制器来处理登录。
-
除了不是tomcats内置authenticaiton,它的JEE内置认证。其中 HttpServletRequest request = (HttpServletRequest) externalContext.getRequest(); request.login(email, user.getPassword());我猜这是相似的?
-
在 server.xml 中它应该是 Context 而不是 context 并放在 Host 元素中。此外,您不应在 server.xml 中定义上下文,它们属于 /conf/Catalina/localhost/
.xml。
标签: java xml jsp tomcat primefaces