用Java Servlets代替CGI
從網絡的早期階段開始,人們就希望他們的網絡服務器不僅能夠顯示靜態文檔,通用網關接口(CGI) 擴展了服務器的能力,但其代價是增加了額外的處理進程。FastCGI則把外部CGI 處理進程同網絡服務器更緊密地集成在一起,另外,對于專有的,諸如NSAPI 和ISAPI 這樣的服務器API,它們直接把外部進程以服務器插件的形式集成到服務器中。現在有了Java servlets,它們的功能強大,可以快速替代你現有的CGI程序。
什么是servlets?
就象applet擴充了網絡瀏覽器的能力一樣,servlets這個Java部件,擴充了網絡服務器的能力。對于任何種類的服務器端的處理,Servlets可以作為server-side includes使用或者作為CGI程序(在JavaSoft的Java Web server中可以作為插件)執行。 Servlets可以移植,不象CGI和專有的API模塊,你可以利用Java的“編寫一次,到處運行”的機制,在你的企業中配置網絡應用程序。Servlets的運行也很穩固,在 servlet 中你創建了一個數據庫連接,下一次你訪問servlet時連接仍然存在,這同CGI 程序不一樣。Servlets也具有擴展性,所以你可以使用面向對象的程序設計方法,來減少開發時間。Servlets可以運行在任何支持servlet的網絡服務器上。目前,servlet SDK除了支持JavaSoft的Java Web server,還支持Netscape, Apache 和IIS,以及大量第三方的網絡服務器。
JSDK導游
為了創建servlets,你需要Java servlet SDK (JSDK),它可以從JavaSoft網站下載。JSDK包含諸如javax.servlet,javax.servlet.http等包,其中包含有你自己創建servlets時所需要的類和接口。對于sun.servlet 包來說,其中包含了網絡服務器用來運行servlets所需要的類。 (對Servlet的支持通常是通過服務器插件的形式)。一旦你有了JSDK,你只要創建GenericServlet類的子類,并且重載若干方法。GenericServlet 定義了你應該重載的三種主要方法: init(), service()和destroy()。
init() :初始化你的servlet,諸如打開數據庫連接。
destroy():在applet運行結束后,清除servlet 自身。
service():每次調用servlet時,就調用service()方法。有兩個對象 ServletRequest和ServletResponse需要傳送給servlet,用于處理客戶請求。
為了幫助處理基于Web 的事務,JSDK 在 javax.servlet.http包中有個HttpServlet類。HttpServlet是從GenericServlet中派生出來的,它提供了service()的一個實現,該實現用于自動處理GET, HEAD和POST的請求。
HttpServlet類中的方法有doGet()和doPost()。一個典型的CGI servlet只需要實現doGet()和doPost()方法。 doGet()和doPost()的參數為HttpServletRequest和HttpServletResponse。
HttpServletRequest是個接口,該接口提供了從客戶的請求獲取信息的一些方法。例如, getParameter()方法返回在客戶請求中的關鍵字/值對(或者從請求串中取得,或者從POSTed數據中取得)。
HttpServletResponse提供了輸出流,使得servlet把HTML格式的輸出返回給客戶。
基本Servlet代碼
代替你的CGI
下面為一段可以取代CGI程序的基本的servlet代碼。Servlet完成如下的簡單事情:列出由HTML表單搜集的關鍵字/值對(key/value)。
BasicCGIServlet處理POST,也用同樣處理GET。所以doPost()和doGet()都調用doService()。doService()可以在子類中重載,以實現更多特定的功能。
import javax.servlet.*;
import javax.servlet.http.*;
import java.io.*;
import java.util.*;
public class BasicCGIServlet extends HttpServlet {
public BasicCGIServlet () {
super();
}
public void doPost (HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
doService(req, resp);
}
public void doGet (HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
doService(req, resp);
}
protected synchronized void doService (HttpServletRequest req,
HttpServletResponse resp) throws ServletException, IOException {
// get an output stream to write to
ServletOutputStream out = resp.getOutputStream();
// set the content type for the response
resp.setContentType (\\"text/html\\");
// optionally you should also set any special content-encoding
// and content length response headers, and return status codes
// write out the response!
out.println (\\"<body
bgcolor=\\\\"white\\\\">\\");
out.println (\\" \\");
out.println (\\"
\\");
for (Enumeration e = req.getParameterNames(); e.hasMoreElements(); ) {
String key = (String) e.nextElement();
out.println (\\"
\\");
}
out.println (\\"
| \\" + key + \\" | \\" + req.getParameter(key) + \\" |
\\");
}
}
當調用req.getParameterNames()時,servlet請求對象讀入表單數據,并且把它解碼為關鍵字/值對(事實上,一旦第一次調用getParameterNames(),或者getParameterValues(),或者getParameter()
時,就進行解碼)。 getParameterNames()返回所有關鍵字的列舉。getParameter()返回同特定關鍵字相對應的值。當servlet請求被解析成關鍵字/值對時,每個關鍵字的值保存在String數組中,以便可以處理一個關鍵字有多個值的情況。調用getParameterValues(),返回的是String數組,而調用 getParameter()后,則僅返回String數組中的第一個元素。
你也許會注意到doService()是個同步化的方法。這是因為servlets 通常是在多線程環境下運行的。因為網絡服務器創建的servlet對象只有一個實例,所以servlet必須能夠對同時發生的請求提供服務。因此,Servlets需要確保:這些請求在訪問共享資源時保持同步。這些共享資源包括實例變量,數據庫連接和文件流等。
運行你的servlet
一旦編寫好servlet,并且編譯成功之后,你可以把它放到網絡服務器中servlet別名目錄中。就同服務器中的cgi-bin別名目錄的作用一樣,任何放在servlet 目錄中的文件,一旦被作為url的一部分被請求時,將被作為servlets執行。例如,BasicCGIServlet可以通過如下的url調用: http://mycompany.com/servlet/BasicCGIServlet。你既可以直接調用該url (并且傳送給servlet一個請求關鍵字/值對的串),也可以通過HTML表單中的一個動作來調用。要了解更多的支持servlet的網絡服務器的信息,請參閱JSDK中的有關文檔信息。
進一步的用法
GenericServlet和 HttpServlet提供了一個構建servlets的固定的基類。通過重載service()方法,你可以在它們的基礎上進行構建。例如,你可以加入對響應緩存的支持(請參見HttpServlet 中的getLastModified()),也可以加入對HTTP 1.1方法的支持,等等。你甚至可以構建一個擴展的模板引擎。(有誰真的喜歡在他們的程序中內置HTML代碼呢?)
另外一個用法是對JSDK進行擴展,使之除了支持標準的application/x-www-form-urlencoded mime 類型之外,還支持其他類型的表單編碼。例如,你可以加入對multipart/form-data mime類型的支持,用于處理通過HTTP上載文件。接口方法getParameterNames(), getParameterValues()等等,都是在sun.servlet包中實現的,所以你需要配置JSDK ,以便加入這些支持。還有一種變通的方法,你可以自己實現有關方法,但那樣做,就需要復制代碼或者改變JSDK的語義。上面的這些方法都是可行的,但是沒有哪一種是完美無缺的。
結論
現在你應該會自己創建Java servlets了,它們可以用來代替傳統的Perl和C/C++ CGI程序。 Java的面向對象的特性和“編寫一次,到處運行”的機制使得Java servlets的編寫很簡單。Servlet的穩固性,可以解決有關狀態管理問題,而這些都是只用一次的CGI程序解決實際問題時通常會遇到的難題。 Servlets可以利用Java語言的所有功能,包括JDBC和RMI。由于大多數網絡服務器都加入了對servlet的支持,Java將迅速成為開發企業級應用程序的一種可選語言。
轉載于:https://www.cnblogs.com/liangxiaofeng/p/4910979.html
總結
以上是生活随笔為你收集整理的用Java Servlets代替CGI的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Codeforces Round #27
- 下一篇: Java学习----运算符与表达式