会话跟踪session

会话跟踪
HTTP是“无状态”协议:客户程序每次读取Web页面,都打开到web服务器的单独的连接,而且,服务器也不自动维护客户的上下文信息。类似客户决定结账时,如何确定之前创建的购物车中哪个属于此客户呢?这种问题有三种解决方案:
cookie、URL重写和隐藏的表单域
cookie处理:
cookie存储购物会话的ID;在后续;连接中,取出当前的会话ID,并使用这个ID从服务器的查找表上提取会话的相关信息。用到两个表:将会话ID与用户关联起来的表和存储用户具体数据的表。
String sessionID = makeUniqueString();
HashMap sessionInfo = new HashMap();
HashMap globalTable = findTableStoringSessions();
globalTable.put(sessionID, sessionInfo);
Cookie sessionCookie = new Cookie("JSESSION", sessionID);
sessionCookie.setPath("/");
response.addCookie(sessionCookie);
这种方式使用cookie是一种绝佳的解决方案,是处理会话常用的方式

url重写:
采用这种方式,客户程序在每个URL尾部加上一些额外数据。这些数据标识当前的会话,服务器将这个标识与它存储的用户相关数据关联起来
隐藏的表单域:
主要缺点是:仅当每个页面都是由表单提交而动态生成才能适用这种方法。

servlet中的会话跟这陪你过
servlet提供一种出色的会话跟踪解决方案:HttpSession API.这个高层接口构筑在cookie和url重写之上
会话跟踪基础:
1、访问与当前请求关联的会话对象
request.getSession获取HttpSession对象。是一个简单的散列表
2、查找与会话相关联的信息
HttpSession的getAttribute
3、存储会话中的信息
setAttribute
4、废弃会话数据
removeAttribute废弃指定的值。invalidate废弃整个会话。logout使客户推出web服务器并作废与用户相关联的所有会话

浏览器会话与服务器会话:
默认,会话跟踪基于存储在浏览器内存中的cookie。

URL重写的话对发往客户的url进行编码:
第一种情况是servlet生成的web页面中含有嵌入的URL。在这种情况下,应该将URL传递给HttpResponse的encodeURL方法。这个方法确定当前是否在使用URL重写,仅在必需时附加会话信息;否则,不做任何更改直接返回传入的URL:
String originalURL = someRelativeOrAbsoluteURL;
String encodeURL = response.encodeURL(originalURL);
out.println("a href="" + encodeURL + "">...</A>")
第二种情况是在sendRedirect调用。这种情况下由于要根据不同的规则确定是否附加会话信息,因此不能使用encodeURL。幸运的是,HttpServletResponse提供encodeRedirectURL方法来处理这种情况:
String originURL = someURL;
String encodedURL = response.encodeRedirectURL(originalURL);
response.sendRedirect(encodedURL);

session:实现购物车的例子:

package com.zhen.test.o5;

import com.zhen.domain.Catalog;
import com.zhen.domain.CatalogItem;
import com.zhen.util.ServletUtilities;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;

/**
 * Created by zhen on 2017-11-15.
 */
public class CatalogPage extends HttpServlet {
    private CatalogItem[] items;
    private String[] itemIDs;
    private String title;

    protected void setItems(String[] itemIDs) {
        this.itemIDs = itemIDs;
        items = new CatalogItem[itemIDs.length];
        for(int i=0; i<items.length; i++){
            items[i] = Catalog.getItem(itemIDs[i]);
        }
    }

    protected void setTitle(String title) {
        this.title = title;
    }

    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        if(items == null){
            resp.sendError(HttpServletResponse.SC_NOT_FOUND, "Missing Items.");
            return;
        }
        resp.setContentType("text/html");
        PrintWriter out = resp.getWriter();
        out.println(ServletUtilities.headWithTitle(title) + "" +
                "<body bgcolor="#fdf5e6">" + title + "</h1>");
        CatalogItem item;
        for(int i=0; i<items.length; i++){
            out.println("<hr>");
            item = items[i];
            if(item == null){
                out.println("<font color="red">Unknow item ID " + itemIDs[i] + "</font>");
            }else{
                out.println();
                String formURL = "com.zhen.test.o5.OrderPage";
                formURL = resp.encodeURL(formURL);
                out.println("<form action="" + formURL + "">" +
                        "<input type="hidden" name="itemID" value="" +item.getItemID()+ "">
" +
                        "<h2>" + item.getShortDescription() + " ($" + item.getCost() + ")</h2>
" +
                        item.getLongDescription() + "
" +
                        "<br>" +
                        "<input type="submit" value="Add to Shopping Cart">
" +
                        "</form>");
            }
        }
        out.println("</body></html>");
    }
}


package com.zhen.test.o5;

import com.zhen.test.o5.CatalogPage;

/**
 * Created by zhen on 2017-11-15.
 */
public class KidsBooksPage extends CatalogPage{
    public void init(){
        String[] ids = {"lewis001", "alexander001", "rowling001"};
        setItems(ids);
        setTitle("All-Time Best Children's Fantasy Books");
    }
}

package com.zhen.test.o5;

import com.zhen.domain.ItemOrder;
import com.zhen.domain.ShoppingCart;
import com.zhen.util.ServletUtilities;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.io.IOException;
import java.io.PrintWriter;
import java.text.NumberFormat;
import java.util.List;

/**
 * Created by zhen on 2017-11-15.
 */
public class OrderPage extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        HttpSession session = req.getSession();
        ShoppingCart cart;
        synchronized (session) {
            cart = (ShoppingCart) session.getAttribute("shoppingCart");
            if(cart == null){
                cart = new ShoppingCart();
                session.setAttribute("shoppingCart", cart);
            }
            String itemID = req.getParameter("itemID");
            if(itemID != null){
                String numItemString = req.getParameter("numItems");
                if(numItemString == null){
                    cart.addItem(itemID);
                }else{
                    int numItems;
                    try{
                        numItems = Integer.parseInt(numItemString);
                    }catch (NumberFormatException nef){
                        numItems = 1;
                    }
                    cart.setNumOrdered(itemID, numItems);
                }
            }
        }
        resp.setContentType("text/html");
        PrintWriter out = resp.getWriter();
        String title = "Status of your Order";
        out.println(ServletUtilities.headWithTitle(title) + "" +
                "<body bgcolor="#fdf5e6">
" +
                "<h1 align="center">" + title + "</h1>");
        synchronized (session){
            List itemsOrdered = cart.getItemsOrdered();
            if(itemsOrdered.size() == 0){
                out.println("<h2><I>No items in your cart...</I></h2");
            }else{
                out.println("<table border=1 align="center">" +
                        "<tr bgcolor="#ffad00">" +
                        "   <th>Item ID</th>" +
                        "   <th>Description</th>" +
                        "   <th>Unit Cost</th>" +
                        "   <th>Number</th>" +
                        "   <th>Total Cost</th>" +
                        "</tr>");
                ItemOrder order;
                NumberFormat format = NumberFormat.getCurrencyInstance();
                for(int i=0; i<itemsOrdered.size(); i++){
                    order = (ItemOrder) itemsOrdered.get(i);
                    out.println("<tr>" +
                            "   <td>" + order.getItemID() + "</td>" +
                            "   <td>" + order.getShortItemDescription() + "</td>" +
                            "   <td>" + format.format(order.getUnitCost()) + "</td>" +
                            "   <td>" +
                                "<form>" +
                                "   <input type="hidden" name="itemID" value="" + order.getItemID() + ""/>
" +
                                "   <input type="text" name="numItems" size=3 value="" + order.getNumItems() + ""/>
" +
                                "   <small><input type="submit" value="Update Order"/></small>" +
                                "</form>" +
                            "   </td>" +
                            "   <td>" + format.format(order.getTotalCost()) + "</td>" +
                            "</tr>");
                }
                String checkoutURL = resp.encodeURL("/webApp1/html/Checkout.html");
                out.println("</table>" +
                        "<form action="" + checkoutURL + "">" +
                        "<big><center>" +
                        "<input type="submit" value="Proceed to Checkout">" +
                        "</center></big></form>");
            }
            out.println("</body></html>");
        }
    }
}

package com.zhen.test.o5;

/**
 * Created by zhen on 2017-11-15.
 */
public class TeachBooksPage extends CatalogPage {
    public void init() {
        String[] ids = {"hall001", "hall002"};
        setItems(ids);
        setTitle("All-Time Best Computer Books");
    }
}

package com.zhen.domain;

/**
 * @author zhen
 * Created by zhen on 2017-10-30.
 */
public class BidInfo {
    private String itemID = "";
    private String itemName = "";
    private String bidderName = "";
    private String emailAddress = "";
    private double bidPrice = 0;
    private boolean autoIncrement = false;

    public String getItemID() {
        return itemID;
    }

    public void setItemID(String itemID) {
        this.itemID = itemID;
    }

    public String getItemName() {
        return itemName;
    }

    public void setItemName(String itemName) {
        this.itemName = itemName;
    }

    public String getBidderName() {
        return bidderName;
    }

    public void setBidderName(String bidderName) {
        this.bidderName = bidderName;
    }

    public String getEmailAddress() {
        return emailAddress;
    }

    public void setEmailAddress(String emailAddress) {
        this.emailAddress = emailAddress;
    }

    public double getBidPrice() {
        return bidPrice;
    }

    public void setBidPrice(double bidPrice) {
        this.bidPrice = bidPrice;
    }

    public boolean isAutoIncrement() {
        return autoIncrement;
    }

    public void setAutoIncrement(boolean autoIncrement) {
        this.autoIncrement = autoIncrement;
    }

    public boolean isComplete() {
        return hasValue(getItemID()) &&
                hasValue(getItemName()) &&
                hasValue(getBidderName()) &&
                hasValue(getEmailAddress()) &&
                (getBidPrice() > 0);
    }

    public boolean isPartlyComplete(){
        boolean flag = (hasValue(getItemID())) ||
                hasValue(getItemName()) ||
                hasValue(getBidderName()) ||
                hasValue(getEmailAddress()) ||
                (getBidPrice() > 0) ||
                isAutoIncrement();
        return flag;
    }

    private boolean hasValue(String val) {
        return (val != null) && (!val.equals(""));
    }

}


package com.zhen.domain;

/**
 * Created by zhen on 2017-11-15.
 */
public class Catalog {
    private static CatalogItem[] items = {
            new CatalogItem("hall001",
                    "<I>Core servlets and JavaServer Pages 2nd Edition<I>",
                    "by Marty Hall and Larry Brown", 39.95),
            new CatalogItem("hall002",
                    "<I>Core web programming , 2nd Edition<I>",
                    "by Marty Hall and Larry Brown",
                    49.99),
            new CatalogItem("lewis001",
                    "<I>The Chronicles of Narina<I>",
                    "ny C.S Lewis",
                    19.95),
            new CatalogItem("alexander001",
                    "<I>The Prydain Series<I>",
                    "by Lloyed Alexander",19.95),
            new CatalogItem("rowling001",
                    "The Harry Potter Series",
                    "by J.K. Rowling",59.95)
    };

    public static CatalogItem getItem(String itemID){
        CatalogItem item;
        if(itemID == null){
            return null;
        }
        for(int i=0; i<items.length; i++){
            item = items[i];
            if(itemID.equals(item.getItemID())){
                return item;
            }
        }
        return null;
    }
}


package com.zhen.domain;

/**
 * Created by zhen on 2017-11-15.
 */
public class CatalogItem {
    private String itemID;
    private String shortDescription;
    private String longDescription;
    private double cost;

    public String getItemID() {
        return itemID;
    }

    public void setItemID(String itemID) {
        this.itemID = itemID;
    }

    public String getShortDescription() {
        return shortDescription;
    }

    public void setShortDescription(String shortDescription) {
        this.shortDescription = shortDescription;
    }

    public String getLongDescription() {
        return longDescription;
    }

    public void setLongDescription(String longDescription) {
        this.longDescription = longDescription;
    }

    public double getCost() {
        return cost;
    }

    public void setCost(double cost) {
        this.cost = cost;
    }

    public CatalogItem(String itemID, String shortDescription, String longDescription, double cost) {
        this.itemID = itemID;
        this.shortDescription = shortDescription;
        this.longDescription = longDescription;
        this.cost = cost;
    }
}

package com.zhen.domain;

/**
 * Created by zhen on 2017-11-15.
 */
public class ItemOrder {
    private CatalogItem item;
    private int numItems;

    public CatalogItem getItem() {
        return item;
    }

    public void setItem(CatalogItem item) {
        this.item = item;
    }

    public int getNumItems() {
        return numItems;
    }

    public void setNumItems(int numItems) {
        this.numItems = numItems;
    }

    public ItemOrder(CatalogItem item, int numItems) {
        this.item = item;
        this.numItems = numItems;
    }

    public ItemOrder(CatalogItem item) {
        this.item = item;
        this.numItems = 1;
    }

    public String getItemID(){
        return getItem().getItemID();
    }

    public String getShortItemDescription(){
        return getItem().getShortDescription();
    }

    public String getLongItemDescription(){
        return getItem().getLongDescription();
    }

    public double getUnitCost(){
        return getItem().getCost();
    }

    public void incrementNumItems(){
        setNumItems(getNumItems() + 1);
    }

    public void cancelOrder(){
        setNumItems(0);
    }

    public double getTotalCost() {
        return getNumItems() * getUnitCost();
    }
}

package com.zhen.domain;

import java.util.ArrayList;
import java.util.List;

/**
 * Created by zhen on 2017-11-15.
 */
public class ShoppingCart {
    private ArrayList itemsOrdered;

    public ShoppingCart(){
        itemsOrdered = new ArrayList();
    }

    public List getItemsOrdered(){
        return itemsOrdered;
    }

    public synchronized void addItem(String itemID) {
        ItemOrder order;
        for(int i=0; i<itemsOrdered.size(); i++){
            order = (ItemOrder) itemsOrdered.get(i);
            if(order.getItemID().equals(itemID)){
                order.incrementNumItems();
                return;
            }
        }
        ItemOrder newOrder = new ItemOrder(Catalog.getItem(itemID));
        itemsOrdered.add(newOrder);
    }

    public synchronized void setNumOrdered(String itemID, int numOrdered) {
        ItemOrder order;
        for(int i=0; i<itemsOrdered.size(); i++){
            order = (ItemOrder) itemsOrdered.get(i);
            if(order.getItemID().equals(itemID)){
                if(numOrdered <= 0){
                    itemsOrdered.remove(i);
                }else{
                    order.setNumItems(numOrdered);
                }
                return;
            }
        }
        ItemOrder newOrder = new ItemOrder(Catalog.getItem(itemID));
        itemsOrdered.add(newOrder);
    }
}

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
    <title>Checking Out</title>
</head>
<body bgcolor="#FDF5E6">
<h1 align="center">Checking Out</h1>
We are sorry, but our electronic credit-card-processing system is currently out of order. Please send a check to:
<pre>
    Marty Hall
    coreservlets.com, Inc.
    6 Meadowsweet Ct., Suite B1
    Reisterstown, MD 21136-6020
    410-429-5535
    hall@coreservlets.com
</pre>
Since we have not yet calculated shipping charges, please sign the check but not fill in the amount. We will generously do that for you.
</body>
</html>

  

原文地址:https://www.cnblogs.com/aigeileshei/p/7840402.html