सर्वलेट क्लास ए में रखें package
सबसे पहले, सर्वलेट क्लास को एक जावा में रखें package
। आपको हमेशा सार्वजनिक रूप से पुन: उपयोग करने योग्य जावा कक्षाएं एक पैकेज में डालनी चाहिए , अन्यथा वे उन कक्षाओं के लिए अदृश्य हैं जो एक पैकेज में हैं, जैसे कि सर्वर। इस तरह आप संभावित पर्यावरण-विशिष्ट समस्याओं को दूर करते हैं। पैकेजलेस सर्वलेट्स केवल विशिष्ट टॉमकट + जेडडीके संयोजनों में काम करते हैं और इस पर कभी भरोसा नहीं किया जाना चाहिए।
एक "सादे" आईडीई परियोजना के मामले में, वर्ग की जरूरत है अपने पैकेज संरचना "जावा संसाधन" फ़ोल्डर के अंदर में रखा करने के लिए किया जा है और इस तरह नहीं "WebContent", वेब JSP के रूप में ऐसी फ़ाइलों के लिए इस है। नीचे एक डिफ़ॉल्ट ग्रहण डायनेमिक वेब प्रोजेक्ट की फ़ोल्डर संरचना का एक उदाहरण है जैसा कि नेविगेटर दृश्य में देखा गया है :
EclipseProjectName
|-- src
| `-- com
| `-- example
| `-- YourServlet.java
|-- WebContent
| |-- WEB-INF
| | `-- web.xml
| `-- jsps
| `-- page.jsp
:
मावेन परियोजना के मामले में, वर्ग को अपने पैकेज संरचना में अंदर रखा जाना चाहिए main/java
और इस तरह उदा नहींmain/resources
, यह गैर-वर्ग फ़ाइलों के लिए है । नीचे एक डिफ़ॉल्ट मावेन वेबप प्रोजेक्ट के फ़ोल्डर संरचना का एक उदाहरण है जैसा कि एक्लिप्स के नेविगेटर दृश्य में देखा गया है :
MavenProjectName
|-- src
| `-- main
| |-- java
| | `-- com
| | `-- example
| | `-- YourServlet.java
| |-- resources
| `-- webapp
| |-- WEB-INF
| | `-- web.xml
| `-- jsps
| `-- page.jsp
:
ध्यान दें कि /jsps
सबफ़ोल्डर कड़ाई से आवश्यक नहीं है। आप इसके बिना भी कर सकते हैं और JSP फाइल को सीधे webcontent / webapp root में डाल सकते हैं, लेकिन मैं इसे आपके सवाल से हटा रहा हूं।
में सर्वलेट URL सेट करें url-pattern
सर्वलेट URL को सर्वलेट मैपिंग के "URL पैटर्न" के रूप में निर्दिष्ट किया गया है। सर्वलेट क्लास के classname / filename की परिभाषा के अनुसार यह बिल्कुल नहीं है। URL पैटर्न को @WebServlet
एनोटेशन के मान के रूप में निर्दिष्ट किया जाना है ।
package com.example; // Use a package!
@WebServlet("/servlet") // This is the URL of the servlet.
public class YourServlet extends HttpServlet { // Must be public and extend HttpServlet.
// ...
}
यदि आप पथ के मापदंडों का समर्थन करना चाहते हैं /servlet/foo/bar
, तो /servlet/*
इसके बजाय URL पैटर्न का उपयोग करें। यह भी देखें / xyz / {value} / परीक्षण, कैसे web.xml में मैप करने के लिए की तरह सर्वलेट और पथ मानकों?
@WebServlet
केवल सर्वलेट 3.0 या नए पर काम करता है
उपयोग करने के लिए @WebServlet
, आपको केवल यह सुनिश्चित करने की आवश्यकता है कि आपकी web.xml
फ़ाइल, यदि कोई हो (यह सर्वलेट 3.0 के बाद से वैकल्पिक है), तो सर्वलेट 3.0+ संस्करण के अनुरूप घोषित किया जाता है और इस प्रकार यह 2.5 संस्करण या निम्न के अनुरूप नहीं है । नीचे एक सर्वलेट 4.0 संगत है (जो टॉमकैट 9+, वाइल्डफली 11+, पयारा 5+, आदि से मेल खाता है)।
<?xml version="1.0" encoding="UTF-8"?>
<web-app
xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
version="4.0"
>
<!-- Config here. -->
</web-app>
या, यदि आप अभी तक सर्वलेट 3.0+ पर नहीं हैं (जैसे कि टॉमकैट 6 या पुराने), तो @WebServlet
एनोटेशन को हटा दें ।
package com.example;
public class YourServlet extends HttpServlet {
// ...
}
और web.xml
इस तरह सर्वलेट रजिस्टर करें:
<servlet>
<servlet-name>yourServlet</servlet-name>
<servlet-class>com.example.YourServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>yourServlet</servlet-name>
<url-pattern>/servlet</url-pattern> <!-- This is the URL of the servlet. -->
</servlet-mapping>
ध्यान दें कि आपको दोनों तरीकों का उपयोग नहीं करना चाहिए। एनोटेशन आधारित कॉन्फ़िगरेशन या XML आधारित कॉन्फ़िगरेशन का उपयोग करें। जब आपके पास दोनों होते हैं, तो XML आधारित कॉन्फ़िगरेशन एनोटेशन आधारित कॉन्फ़िगरेशन को ओवरराइड करेगा।
बिल्ड / परिनियोजन का सत्यापन करना
यदि आप एक बिल्ड टूल जैसे कि एक्लिप्स और / या मावेन का उपयोग कर रहे हैं, तो आपको यह सुनिश्चित करने की आवश्यकता है कि संकलित सर्वलेट क्लास फ़ाइल /WEB-INF/classes
उत्पादित WAR फ़ाइल के फ़ोल्डर में इसकी पैकेज संरचना में रहती है । के मामले में package com.example; public class YourServlet
, यह स्थित होना चाहिए /WEB-INF/classes/com/example/YourServlet.class
। अन्यथा आप @WebServlet
भी 404 त्रुटि के मामले में, या <servlet>
नीचे की तरह HTTP 500 त्रुटि के मामले में सामना करेंगे :
HTTP स्थिति 500
सर्वलेट क्लास com.example.YourServlet को त्वरित करने में त्रुटि
और सर्वर लॉग में खोजें java.lang.ClassNotFoundException: com.example.YourServlet
, उसके बाद ए , इसके java.lang.NoClassDefFoundError: com.example.YourServlet
बाद में javax.servlet.ServletException: Error instantiating servlet class com.example.YourServlet
।
यह सत्यापित करने का एक आसान तरीका है कि सर्वलेट को सही ढंग से संकलित किया गया है और क्लासपाथ में रखा गया है, ताकि बिल्ड टूल को WAR फ़ाइल (उदाहरण के लिए राइटक्लिक प्रोजेक्ट, एक्लिप्स में WAR फ़ाइल ) का उत्पादन करने दिया जाए और फिर एक ज़िप टूल के साथ इसकी सामग्री का निरीक्षण किया जाए। यदि सर्वलेट क्लास गायब है /WEB-INF/classes
, या यदि निर्यात में त्रुटि होती है, तो प्रोजेक्ट बुरी तरह से कॉन्फ़िगर किया गया है या कुछ IDE / प्रोजेक्ट कॉन्फ़िगरेशन डिफॉल्ट्स को गलती से वापस कर दिया गया है (जैसे प्रोजेक्ट> बिल्ड स्वचालित रूप से ग्रहण में अक्षम कर दिया गया है)।
आपको यह भी सुनिश्चित करने की आवश्यकता है कि प्रोजेक्ट आइकन में कोई रेड क्रॉस नहीं है जो एक बिल्ड त्रुटि का संकेत है। आप समस्याओं को देखने में सटीक त्रुटि पा सकते हैं ( विंडो> शो देखें> अन्य ... )। आमतौर पर त्रुटि संदेश ठीक Googlable है। यदि आपके पास कोई सुराग नहीं है, तो सबसे अच्छा है कि खरोंच से पुनः आरंभ करें और किसी भी आईडीई / प्रोजेक्ट कॉन्फ़िगरेशन डिफॉल्ट को न छूएं। यदि आप ग्रहण का उपयोग कर रहे हैं, तो आप निर्देश पा सकते हैं कि मैं अपने ग्रहण परियोजना में javax.servlet एपीआई का आयात कैसे करूँ?
व्यक्तिगत रूप से सर्वलेट का परीक्षण
बशर्ते कि सर्वर चलता है localhost:8080
, और यह कि WAR को सफलतापूर्वक एक संदर्भ पथ पर तैनात किया जाता है /contextname
(जो IDE प्रोजेक्ट नाम, केस सेंसिटिव!) के लिए डिफॉल्ट करता है, और सर्वलेट ने इसके आरंभीकरण को विफल नहीं किया है (किसी भी तैनाती के लिए सर्वर लॉग पढ़ें /) सर्वलेट सफलता / विफल संदेश और वास्तविक संदर्भ पथ और सर्वलेट मैपिंग), तब URL पैटर्न वाला एक सर्वलेट /servlet
उपलब्ध है http://localhost:8080/contextname/servlet
।
आप इसे सीधे ब्राउजर के एड्रेस बार में सीधे दर्ज कर सकते हैं ताकि इसे अनजाने में टेस्ट किया जा सके। यदि इसका doGet()
ठीक से ओवरराइड और कार्यान्वित किया जाता है, तो आपको ब्राउज़र में इसका आउटपुट दिखाई देगा। या यदि आपके पास कोई भी नहीं है doGet()
या यदि यह गलत तरीके से कॉल करता है super.doGet()
, तो " HTTP 405: HTTP पद्धति GET इस URL द्वारा समर्थित नहीं है " त्रुटि दिखाई जाएगी (जो कि 404 के मुकाबले 404 से बेहतर है, प्रमाण है कि सर्वलेट स्वयं वास्तव में पाया जाता है)।
ओवरराइड service()
करना एक बुरा अभ्यास है, जब तक कि आप एमवीसी ढांचे को सुदृढ़ नहीं कर रहे हैं - जो कि बहुत संभव नहीं है अगर आप केवल सर्वलेट्स के साथ शुरू कर रहे हैं और वर्तमान प्रश्न में वर्णित समस्या के रूप में स्पष्ट हैं;) डिजाइन पैटर्न वेब आधारित एप्लिकेशन भी देखें ।
भले ही, सर्वलेट पहले से ही 404 लौटाया जाता है जब सामान्य रूप से परीक्षण किया जाता है, तो इसके बजाय HTML फॉर्म के साथ प्रयास करना पूरी तरह से व्यर्थ है। तार्किक रूप से, इसलिए सर्वलेट से 404 त्रुटियों के बारे में प्रश्नों में किसी भी HTML फॉर्म को शामिल करना पूरी तरह से व्यर्थ है।
HTML से सर्वलेट URL को संदर्भित करना
एक बार जब आप यह सत्यापित कर लेते हैं कि व्यक्तिगत रूप से मंगाने पर सर्वलेट ठीक काम करता है, तो आप HTML को आगे बढ़ा सकते हैं। HTML फॉर्म के साथ आपकी ठोस समस्या के रूप में, <form action>
मान को एक मान्य URL होने की आवश्यकता है। वही लागू होता है <a href>
। आपको यह समझने की आवश्यकता है कि URL कितने पूर्ण / सापेक्ष हैं। आप जानते हैं, एक URL एक वेब एड्रेस होता है, जैसा कि आप webbrowser के एड्रेस बार में दर्ज / देख सकते हैं। यदि आप किसी रिश्तेदार URL को फ़ॉर्म क्रिया के रूप में निर्दिष्ट कर रहे हैं, अर्थात इस http://
योजना के बिना , तो यह वर्तमान URL के सापेक्ष हो जाता है जैसा कि आप अपने वेबसर्वर के एड्रेस बार में देखते हैं। यह इस प्रकार सर्वर के WAR फ़ोल्डर संरचना में JSP / HTML फ़ाइल स्थान के सापेक्ष बिल्कुल नहीं है जैसा कि कई शुरुआती लोग सोचते हैं।
तो, यह सोचते हैं कि HTML प्रपत्र के साथ JSP पेज द्वारा खोला जाता है http://localhost:8080/contextname/jsps/page.jsp
, और आप में स्थित एक सर्वलेट को प्रस्तुत करने की आवश्यकता http://localhost:8080/contextname/servlet
है, यहाँ कई मामलों (ध्यान दें कि आप सुरक्षित रूप से स्थानापन्न कर सकते हैं <form action>
के साथ <a href>
यहाँ):
फ़ॉर्म कार्रवाई एक अग्रणी स्लैश के साथ एक URL के लिए सबमिट होती है।
<form action="/servlet">
प्रमुख स्लैश /
URL को डोमेन के सापेक्ष बनाता है, इस प्रकार फ़ॉर्म सबमिट हो जाएगा
http://localhost:8080/servlet
लेकिन इसकी संभावना 404 होगी क्योंकि यह गलत संदर्भ में है।
फॉर्म कार्रवाई एक अग्रणी स्लैश के बिना एक URL के लिए प्रस्तुत करता है।
<form action="servlet">
यह URL को वर्तमान URL के वर्तमान फ़ोल्डर के सापेक्ष बनाता है, इस प्रकार फ़ॉर्म सबमिट होगा
http://localhost:8080/contextname/jsps/servlet
लेकिन यह संभवतः 404 में परिणाम देगा क्योंकि यह गलत फ़ोल्डर में है।
प्रपत्र एक URL पर जाता है, जो एक फ़ोल्डर ऊपर जाता है।
<form action="../servlet">
यह एक फ़ोल्डर ऊपर जाएगा (बिल्कुल स्थानीय डिस्क फ़ाइल सिस्टम पथों की तरह!), इस प्रकार फ़ॉर्म सबमिट हो जाएगा
http://localhost:8080/contextname/servlet
यह एक काम करना चाहिए!
हालाँकि, विहित दृष्टिकोण URL डोमेन-सापेक्ष बनाने के लिए है ताकि आपको एक बार फिर से URL को ठीक करने की आवश्यकता न पड़े जब आप JSP फ़ाइलों को किसी अन्य फ़ोल्डर में ले जाएँ।
<form action="${pageContext.request.contextPath}/servlet">
यह उत्पन्न करेगा
<form action="/contextname/servlet">
इस प्रकार हमेशा सही URL सबमिट करना होगा।
HTML में सीधे उद्धरणों का उपयोग करें
आपको यह सुनिश्चित करने की आवश्यकता है कि आप HTML विशेषताओं में सीधे उद्धरणों का उपयोग कर रहे हैं जैसे कि action="..."
या action='...'
इस प्रकार या जैसे घुंघराले उद्धरण नहीं । HTML में घुंघराले उद्धरण समर्थित नहीं हैं और वे बस मूल्य का हिस्सा बन जाएंगे।action=”...”
action=’...’
यह सभी देखें:
HTTP स्थिति 404 त्रुटि के अन्य मामले: