java ee用户登录

我在上一篇文章中介绍了Application类,您可以在其中设置后端服务。 我添加的一个示例服务是UserService 。 该服务将加载包含用户名和密码集的Java用户属性文件; 稍后将用于对用户进行身份验证以登录到Web应用程序。 现在,我将展示如何使用标准Servlet API以及此后端服务完成登录部分。

从高层次上讲,我们希望将某些Web资源(这意味着Servlet提供的某些URL,例如“ / sysprops”或“ / user”)限制为仅在我们的用户属性文件中已知的客户端用户。 用户可以使用匹配的密码来标识自己。 通常使用用户登录表单来完成此操作,对其进行身份验证,然后将登录令牌插入Http Session范围空间。 然后可以使用此登录令牌来验证是否允许用户访问受限资源。 我们只对单一授权感兴趣(未定义任何角色,任何登录的用户都可以访问任何受保护的URL。)

SysPropsServlet提供的我以前的SysPropsServlet ,您已经看到一个映射到“ / sysprops” URL的示例,该示例仅生成系统信息HTML表。 这些是敏感信息,因此我们要保护此URL。 我们将需要创建一个实现javax.servlet.Filter接口的类,然后使用此过滤器添加“ / sysprops” URL,以便它可以在实际的Servlet之前对请求进行预处理。 该过滤器使我们可以检查HTTP请求对象,并在需要时中止请求,从而限制了访问。

package zemian.servlet3example.web;import java.io.IOException;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.annotation.WebFilter;
import javax.servlet.http.HttpServletRequest;
import zemian.service.logging.Logger;@WebFilter(urlPatterns={"/sys-props", "/user"})
public class LoginRequiredFilter implements Filter {private static final Logger LOGGER = new Logger(LoginRequiredFilter.class);public static final String LOGIN_REDIRECT = "LOGIN_REDIRECT";@Overridepublic void init(FilterConfig filterConfig) throws ServletException {}@Overridepublic void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {if (request instanceof HttpServletRequest) {HttpServletRequest req = (HttpServletRequest) request;LOGGER.trace("Checking LoginSession token for uri=%s", req.getRequestURI());LoginSession loginSession = LoginServlet.getOptionalLoginSession(req);if (loginSession == null) {LOGGER.debug("No LoginSession token found; forwarding request to login page.");// We need to save the old URI so we can auto redirect after login.req.setAttribute(LOGIN_REDIRECT, req.getRequestURI());req.getRequestDispatcher("/login").forward(request, response);return;} else {LOGGER.debug("Request allowed using LoginSession token=%s", loginSession.getId());}}chain.doFilter(request, response);}@Overridepublic void destroy() {}}

请注意,您可以配置此过滤器以匹配要保护的多个URL。 您甚至可以使用通配符模式,例如“ / *”,它将保护应用程序中的每个URL! 过滤器只是在Http Session空间中LoginSession我们稍后将创建的LoginSession对象。 如果找到了它,则它使请求通过,否则它将重定向到LoginServlet页面,该页面由LoginServlet类提供服务(请注意RETURN语句用于尽早退出filter方法而不调用filter链!)。

LoginServlet类是一种表单处理Servlet,它将提示用户输入用户名和密码。 如果成功,那么我们将LoginSession令牌对象插入到HttpSession空间中,这就是上面的过滤器正在寻找的内容。 这是处理Servlet代码。

package zemian.servlet3example.web;import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import zemian.service.logging.Logger;
import zemian.servlet3example.service.Application;
import zemian.servlet3example.service.UserService;@WebServlet("/login")
public class LoginServlet  extends HtmlWriterServlet {private static final Logger LOGGER = new Logger(LoginServlet.class);@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {HtmlWriter html = createHtmlWriter(req, resp);String message;// Check to see if we are doing logout or not.LoginSession loginSession = getOptionalLoginSession(req);if (loginSession != null && req.getParameter("logout") != null) {logout(req);message = "Your have successfully logged out.";} else {   message = (String)req.getAttribute("message");if (message == null)message = "";}  // Show a login formString redirectUri = (String)req.getAttribute(LoginRequiredFilter.LOGIN_REDIRECT);String redirectHtmlTag = "";if (redirectUri != null) {redirectHtmlTag = "<input type='hidden' name='redirectUri' value='" + redirectUri + "'/>";}html.header().h(1, "Please Login").p(message).println("<form method='post' action='login'>").println(redirectHtmlTag).println("<p/>Username: <input type='text' name='username'/>").println("<p/>Password: <input type='password' name='password'/>").println("<p/><input type='submit' value='Submit'/>").println("</form>").footer();}@Overrideprotected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {LOGGER.debug("Processing login form.");if (login(req)) {// Login succeed, we should auto redirect user if exists.String redirectUri = req.getParameter("redirectUri");if (redirectUri != null) {LOGGER.debug("Redirect after login to: %s", redirectUri);resp.sendRedirect(redirectUri);return;}}// Show the form again in case login failed or user didn't provide a redirectdoGet(req, resp);}   protected LoginSession createLoginSession(HttpServletRequest req, String username) {LoginSession result = new LoginSession(username);req.getSession(true).setAttribute(LoginSession.LOGIN_SESSION_KEY, result);return result;}protected void removeLoginSession(HttpServletRequest req) {HttpSession session = req.getSession(false);if (session != null) {session.removeAttribute(LoginSession.LOGIN_SESSION_KEY);}}private boolean login(HttpServletRequest req) throws IOException {String username = req.getParameter("username");String password = req.getParameter("password");UserService userService = Application.getInstance().getUserService();if (userService.validate(username, password)) {LOGGER.info("User %s logged in successfully.", username);// Create Session Data here after successful authenticated.LoginSession loginsession = getOptionalLoginSession(req);if (loginsession == null) {createLoginSession(req, username);req.setAttribute("message", "You have successfully logged in.");} else {req.setAttribute("message", "You already have logged in.");            }} else {LOGGER.info("User %s failed to login.", username);req.setAttribute("message", "Invalid login.");}return true;}/** Return LoginSession if found in HttpSession scope, else return NULL value. */public static LoginSession getOptionalLoginSession(HttpServletRequest req) {LoginSession result = null;HttpSession session = req.getSession(false);if (session != null)result = (LoginSession)session.getAttribute(LoginSession.LOGIN_SESSION_KEY);return result;}
}

LoginServlet类内部,我们使用UserService服务来验证用户名和密码。 我们显示带有GET请求的登录表单,然后通过POST操作处理登录。 检查用户名和密码后,我们将创建LoginSession对象。 这只是表示会话令牌的简单POJO。 您可以保留所需的任何用户信息。 我不会在这里列出,但是您可以在GitHub上浏览它。 请注意,您应该使它可序列化,因为存储在HttpSession中的任何数据都可能会被应用程序服务器序列化/反序列化。

还要注意,我也已经将Logout功能实现到LoginServlet类中。 您只需传递“注销”查询参数,它将被检测到并从会话中删除登录令牌。 这样做时,请确保使HttpSession本身无效,只是为了保证安全。 我还公开了一个静态帮助器getOptionalLoginSessiongetOptionalLoginSession在少数几个类之间使用,以检查用户是否已登录。

这几个类很简单,但是展示了如何使用Servlet Filter和Servlet来管理Session数据。 这种编程模式允许用户通过应用程序拥有自己的浏览会话和隐私。

如果要在GlassFish服务器中运行我的servlet3-example ,则可以使用here中列出的任何用户登录。

翻译自: https://www.javacodegeeks.com/2015/01/ee-servlet-3-developing-user-login-with-session-and-filter.html

java ee用户登录

java ee用户登录_EE Servlet 3:使用会话和过滤器开发用户登录相关推荐

  1. EE Servlet 3:使用会话和过滤器开发用户登录

    我在上一篇文章中介绍了Application类,您可以在其中设置后端服务. 我添加的一个示例服务是UserService . 该服务将加载包含用户名和密码集的Java用户属性文件: 稍后将用于对用户进 ...

  2. java ee jsp_EE JSP:Servlet的反向外套

    java ee jsp 仅当页面数量少或需要对生成的内容(二进制PDF等)进行精细控制时,才可以从Servlet生成HTML. 对于大多数应用程序,输出将是HTML,我们需要一种更好的方法来完成此操作 ...

  3. java ee 程序_第一个 JavaEE 应用程序 - JavaWeb 入门开发教程

    第一个 JavaEE 应用程序 JavaEE 是 Java Web 开发当中事实上的标准,诸多框架也都是建立在 JavaEE 的 API 基础之上的.为了从头理解 Java Web 开发,我们将从一个 ...

  4. Java Web学习总结(34)——拦截器和过滤器的差异总结

    过滤器和拦截器的区别: ①拦截器是基于Java的反射机制的,而过滤器是基于函数回调. ②拦截器不依赖与servlet容器,过滤器依赖与servlet容器. ③拦截器只能对action请求起作用,而过滤 ...

  5. Java+MyEclipse+Tomcat (二)配置Servlet及简单实现表单提交

    在Java EE应用编程中Servlet是基础,JSP是建立在Servlet基础之上的,其他Web框架如Struts.WebWork和Spring MVC都是基于Servlet的.本文主要讲述MyEc ...

  6. oidc_使用Java EE和OIDC构建Java REST API

    oidc "我喜欢编写身份验证和授权代码." 〜从来没有Java开发人员. 厌倦了一次又一次地建立相同的登录屏幕? 尝试使用Okta API进行托管身份验证,授权和多因素身份验证. ...

  7. 使用Java EE和OIDC构建Java REST API

    "我喜欢编写身份验证和授权代码." 〜从来没有Java开发人员. 厌倦了一次又一次地建立相同的登录屏幕? 尝试使用Okta API进行托管身份验证,授权和多因素身份验证. Java ...

  8. Java EE 8发生了什么?

    Java EE 8的工作进展顺利. 是时候赶上了! 无需费力就可以潜入- 不要忘记Java EE 7-.. 围绕三个重要主题 HTML 5对齐–用于WebSocket的Java API(JSR 356 ...

  9. Java EE:更名实属无奈,未来路在何方?

    点击关注 InfoQ,置顶公众号 接收程序员的 8 点技术早餐 作者|Jean-François James 编辑|薛命灯.郭蕾 1999 年,Sun 公司正式发布了 J2EE 的第一个版本.到现在, ...

最新文章

  1. BZOJ 2326: [HNOI2011]数学作业( 矩阵快速幂 )
  2. 033-Unit 12 Introduction to String Processiong
  3. 通用无线设备对码软件_珞光全新发布国产通用软件无线电平台 :USRP-LW N310!珞光品牌已实现国产替代...
  4. SpringMVC报错The request sent by the client was syntactically incorrect ()
  5. C#注册类方法到Lua
  6. JDBC插入百万数据,不到5秒!
  7. 游戏开发:Html5 虚拟摇杆控制人物移动
  8. FCKeditor使用
  9. EOVA的下拉级联实现过程
  10. PowerDesign安装教程
  11. python网络测速_Linux下3种常用的网络测速工具
  12. ruby语言学习-开启篇
  13. pow函数php,PHP pow( )用法及代码示例
  14. wpf初学者-wpf控件简单介绍
  15. NFS服务器配置与管理笔记
  16. 客户端与服务器交互的功能,如何进行测试?
  17. 聊天机器人chatbot搭建及思考(TensorFlow)(附代码)
  18. Mysql的避坑---- The error may involve defaultParameterMap #The error occurred while setting parameters
  19. IE8和IE9发送跨域请求
  20. 计算机网络access code,access code

热门文章

  1. P2495-[SDOI2011]消耗战【虚树,dp】
  2. 洛谷P3845-球赛【离散化,贪心】
  3. codeforces1451 D. Circle Game
  4. 【费用流】【线性规划】志愿者招募(luogu 3980)
  5. 【Trie】阅读理解(luogu 3879/ybtoj Trie-4)
  6. 费用流-Wannafly Day2 TwoGraph-神题
  7. codeforces E. Game with String 概率
  8. 动态规划训练20 [Treats for the Cows POJ - 3186 ]
  9. 第三章用sql语句操作数据
  10. 快速排序+时间测试(yyds)