CodeGym /Blog Java /rawak /Mencipta aplikasi web mudah menggunakan servlet dan JSP (...
John Squirrels
Tahap
San Francisco

Mencipta aplikasi web mudah menggunakan servlet dan JSP (bahagian 1)

Diterbitkan dalam kumpulan
Pengetahuan yang diperlukan untuk memahami artikel: Anda sudah lebih kurang memahami Java Core dan ingin melihat teknologi JavaEE dan pengaturcaraan web . Adalah paling masuk akal untuk anda sedang mengkaji pencarian Java Collections , yang memperkatakan topik yang hampir dengan artikel itu.
Mencipta aplikasi web mudah menggunakan servlet dan JSP (bahagian 1) - 1
Bahan ini adalah kesinambungan logik artikel saya Mencipta projek web termudah dalam IntelliJ Idea Enterprise . Dalam artikel itu, saya menunjukkan cara membuat templat projek web yang berfungsi. Kali ini saya akan menunjukkan kepada anda cara mencipta aplikasi web yang ringkas tetapi benar-benar menarik menggunakan Java Servlet API dan JavaServer Pages API . Permohonan kami akan mempunyai halaman utama dengan dua pautan:
  • pautan ke halaman untuk menambah pengguna;
  • pautan ke senarai pengguna.
Seperti sebelum ini, saya akan menggunakan IntelliJ Idea Enterprise Edition , Apache Maven (kami hanya akan menyambung beberapa kebergantungan), dan Apache Tomcat . Pada akhirnya, kami akan "mencantikkan" aplikasi kami menggunakan rangka kerja W3.CSS . Kami akan menganggap bahawa anda sudah mempunyai projek kosong yang kini akan kami tambahkan. Jika tidak, jalankan artikel pertama dan buat satu. Ia akan mengambil masa beberapa minit sahaja :)

Sedikit tentang struktur aplikasi masa hadapan kami

Halaman utama kami (/) akan menjadi halaman HTML statik yang paling biasa dengan pengepala dan dua pautan/butang:
  • tambah pengguna baharu (menavigasi ke / tambah );
  • lihat senarai pengguna (menavigasi ke / senarai ).
Tomcat akan menangkap permintaan untuk alamat ini dan menghantarnya ke salah satu daripada dua servlet yang akan kami buat (kami akan menentukan pemetaan dalam web.xml ). Servlet kemudiannya akan memproses permintaan, menyediakan data (atau menyimpan data, jika kami menambah pengguna) dan memindahkan kawalan ke fail JSP yang sesuai , yang kemudiannya "memberi" hasilnya. Kami akan menyimpan data dalam senarai vanila biasa (Senarai).

Buat halaman utama statik

Jika anda index.jsp dalam folder web anda, padamkannya. Sebaliknya, buat fail HTML ringkas yang dipanggil index.html dalam folder ini:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>My super project!</title>
</head>
<body>
    <!-- header -->
    <div>
        <h1>Super app!<//h1>
    </div>

    <div>       <!-- content -->
        <div>    <!-- button holder -->
            <button onclick="location.href='/list'">List users<//button>
            <button onclick="location.href='/add'">Add user<//button>
        </div>
    </div>
</body>
</html>
Tidak ada yang rumit di sini. Dalam teg tajuk , kami menunjukkan tajuk halaman kami. Dalam isi halaman, kami mempunyai dua div utama: pengepala dan kandungan . Div kandungan termasuk pemegang untuk butang kami. Dan di sana kami mempunyai dua butang yang membawa anda ke alamat yang sepadan dengan satu klik. Anda boleh menjalankan projek dan melihat rupanya sekarang. Jika anda mengklik pada butang, anda mendapat halaman ralat 404, kerana kami halaman yang sepadan belum wujud lagi. Tetapi kita boleh tahu bahawa butang berfungsi. Ambil perhatian bahawa ini bukan pendekatan yang paling universal: jika JavaScript dimatikan dalam penyemak imbas, maka butang ini tidak akan berfungsi. Tetapi kami akan menganggap bahawa tiada siapa yang melumpuhkan JavaScript. :) Jelas sekali, anda boleh bertahan dengan pautan mudah, tetapi saya lebih suka butang. Anda boleh melakukannya mengikut kehendak anda. Dan jangan risau tentang fakta bahawa contoh saya akan mempunyai banyak div . Kami akan mengisinya dengan gaya kemudian, dan semuanya akan kelihatan lebih cantik. :)

Cipta fail JSP untuk memaparkan hasilnya

Dalam direktori web yang sama , buat folder tempat kami akan menambahkan fail JSP kami . Saya memanggilnya ' pandangan ', tetapi sekali lagi anda boleh membuat improvisasi. Dalam folder ini, kami akan mencipta dua fail JSP:
  • add.jsp — halaman untuk menambah pengguna;
  • list.jsp — halaman untuk memaparkan senarai pengguna.
Berikan pengepala halaman yang sesuai kepada mereka. Sesuatu seperti " Tambah pengguna baharu " dan " Senarai pengguna ", dan kami akan membiarkannya begitu sahaja.

Buat dua servlet

Servlets akan menerima dan memproses permintaan yang Tomcat hantar kepada mereka. Dalam folder src/main/java , buat pakej aplikasi , di mana kami akan meletakkan kod sumber kami. Pakej lain juga akan pergi ke sana. Jadi, untuk mengelakkan pakej ini daripada dicipta di dalam satu sama lain, kami akan mencipta beberapa kelas dalam pakej aplikasi (kami akan memadamkannya kemudian). Sekarang buat tiga pakej berbeza dalam pakej aplikasi :
  • entiti — entiti kami (kelas yang menerangkan objek pengguna) pergi ke sini;
  • model — di sinilah model kita pergi (kita akan bercakap tentang perkara ini sedikit kemudian);
  • servlets — dan di sinilah servlet kami pergi.
Setelah anda melakukan ini, anda boleh memadamkan kelas itu dengan tenang daripada pakej apl (jika anda menciptanya, sudah tentu). Dalam pakej servlets , buat dua kelas:
  • AddServlet — memproses permintaan yang dihantar ke / menambah ;
  • ListServlet — memproses permintaan yang dihantar ke / senarai .

Menyambung kebergantungan dalam Maven

Tomcat 9 .* melaksanakan spesifikasi untuk Servlet 4.0 dan JavaServer Pages 2.3 . Itulah yang dinyatakan dalam baris kedua perenggan pertama dokumentasi rasmi Tomcat 9. Ini bermakna jika anda, seperti saya, menggunakan versi Tomcat ini , maka kod yang anda akan tulis dan jalankan akan menggunakan versi ini. Tetapi kami ingin mempunyai spesifikasi ini dalam projek kami, supaya kod kami, yang menggunakannya, sekurang-kurangnya berjaya disusun. Dan untuk melakukan ini, kami perlu memuatkannya ke dalam projek kami. Di sinilah Maven datang untuk menyelamatkan.

Peraturan umum adalah ini: jika anda perlu menyambungkan sesuatu ke projek anda menggunakan Maven:

  • pergi ke laman web repositori dari Maven;
  • cari versi perpustakaan yang diperlukan;
  • dapatkan kod kebergantungan yang perlu ditampal ke dalam pom.xml anda;
  • tampal! :)
Mari kita mulakan. Mula-mula, sediakan fail POM . Di suatu tempat selepas entri /version , tetapi sebelum /project , masukkan yang berikut:

<dependencies>

</dependencies>
Kami melakukan ini untuk menunjukkan bahawa kami akan menyenaraikan kebergantungan yang diperlukan dalam teg ini. Sekarang pergi ke mvnrepository.com . Terdapat medan carian di bahagian atas. Untuk memulakan, cari ' servlet '. Hasil pertama, yang telah digunakan lebih daripada tujuh ribu kali, sesuai dengan kami. Ingat, kami memerlukan versi 4.0 (untuk Tomcat 9). Versi lain mungkin sesuai untuk pelaksanaan yang lebih lama. Ini adalah versi yang agak baru-baru ini, jadi tidak banyak kegunaannya. Tetapi kita memerlukannya. Halaman dibuka di mana anda boleh mendapatkan kod untuk pergantungan ini untuk pelbagai pengurus pakej, atau anda boleh memuat turunnya sahaja. Tetapi kerana kami ingin menyambungkannya menggunakan Maven, kami akan memilih kod pada tab Maven. Kami menyalin dan menampal ke bahagian pergantungan fail POM kami. Jika anda mendapat pemberitahuan yang bertanya sama ada anda mahu mendayakan autoimport di penjuru kanan sebelah bawah IDEA , teruskan dan bersetuju dengannya. Jika anda menolak secara tidak sengaja, pergi ke " Tetapan " dan hidupkan import automatik secara manual: Tetapan (Ctrl + Alt + S) -> Bina, Pelaksanaan, Penggunaan -> Maven -> Mengimport .dan fail konfigurasi IDEA untuk projek ini disegerakkan. Mengikut prinsip yang sama, kami akan mencari dan menyambungkan JavaServer Pages 2.3 (cari "JSP"). Dan memandangkan kita telah pun memulakan Maven, mari kita beritahu bahawa fail sumber kita mengikut sintaks Java 8, dan kita perlu menyusunnya menjadi kod bait untuk versi itu. Selepas semua langkah ini, pom.xml kami akan kelihatan seperti ini:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>cc.codegym.info.fatfaggy</groupId>
    <artifactId>my-super-project</artifactId>
    <version>1.0-SNAPSHOT</version>

    <properties>
        <maven.compile.source>1.8</maven.compile.source>
        <maven.compile.target>1.8</maven.compile.target>
    </properties>

    <dependencies>
        <!-- Servlet API 4.0 for tomcat 9 -->
        <dependency>
            <groupId>javax.servlet</groupId>
            <artifactId>javax.servlet-api</artifactId>
            <version>4.0.0</version>
            <scope>provided</scope>
        </dependency>

        <!-- JavaServer Pages API 2.3 for tomcat 9 -->
        <dependency>
            <groupId>javax.servlet.jsp</groupId>
            <artifactId>javax.servlet.jsp-api</artifactId>
            <version>2.3.1</version>
            <scope>provided</scope>
        </dependency>
    </dependencies>

</project>

Jadikan servlet kami menjadi servlet sebenar

Pada masa ini, pasangan servlet yang kami cipta sebenarnya adalah kelas biasa. Mereka tidak mempunyai sebarang fungsi. Tetapi kini kami telah menyambungkan Servlet API kepada projek kami, dan sewajarnya kami boleh menggunakan kelasnya. Untuk menjadikan servlet kami "sebenar", apa yang perlu kami lakukan ialah menjadikannya mewarisi kelas HttpServlet .

Pemetaan atau markup

Sekarang adalah baik untuk memberitahu Tomcat bahawa permintaan untuk alamat / tambah diproses oleh AddServlet kami , dan permintaan untuk alamat / senarai dikendalikan oleh ListServlet . Proses ini dipanggil pemetaan (markup). Ini dilakukan dalam web.xml menggunakan prinsip yang sama:
  • untuk memulakan, terangkan servlet (berikan beberapa nama dan nyatakan laluan ke kelas itu sendiri);
  • kemudian ikat servlet ini ke alamat tertentu (nyatakan nama servlet, yang baru kami berikan, dan nyatakan alamat yang permintaannya harus dihantar ke servlet ini).
Terangkan servlet:

<servlet>
    <servlet-name>add</servlet-name>
    <servlet-class>app.servlets.AddServlet</servlet-class>
</servlet>
Sekarang ikatkannya ke alamat:

<servlet-mapping>
    <servlet-name>add</servlet-name>
    <url-pattern>/add</url-pattern>
</servlet-mapping>
Seperti yang anda lihat, nama servlet adalah sama dalam kedua-dua kes. Akibatnya, Tomcat tahu bahawa jika permintaan untuk /add diterima, ia mesti dihantar ke app.servlets.AddServlet. Kami melakukan perkara yang sama dengan servlet kedua. Pada akhirnya, web.xml kami mempunyai lebih kurang kandungan berikut:

<?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_3_1.xsd"
         version="3.1">

    <!-- add servlet -->
    <servlet>
        <servlet-name>add</servlet-name>
        <servlet-class>app.servlets.AddServlet</servlet-class>
    </servlet>

    <servlet-mapping>
        <servlet-name>add</servlet-name>
        <url-pattern>/add</url-pattern>
    </servlet-mapping>

    <!-- list servlet -->
    <servlet>
        <servlet-name>list</servlet-name>
        <servlet-class>app.servlets.ListServlet</servlet-class>
    </servlet>

    <servlet-mapping>
        <servlet-name>list</servlet-name>
        <url-pattern>/list</url-pattern>
    </servlet-mapping>
</web-app>
By the way, kami tidak membuat markup untuk halaman utama (/). Hakikatnya kita tidak memerlukannya dalam kes ini. Halaman utama kami ialah fail HTML ringkas yang hanya memaparkan dua butang. Ia tidak mempunyai kandungan dinamik, jadi kami tidak perlu mencipta servlet berasingan untuk permintaan daripada / yang tidak akan melakukan apa-apa selain melaksanakan pelaksanaan ke beberapa JSP (yang juga perlu dibuat) untuk menarik dua butang untuk kami. Kami tidak memerlukan ini. Halaman statik sesuai dengan kita. Apabila Tomcat menerima permintaan, ia akan menyemak sama ada terdapat satu servlet yang boleh memproses permintaan untuk alamat itu, dan kemudian akan melihat bahawa alamat ini sebenarnya sudah mengandungi fail HTML sedia, yang akan dihidangkan. Kami boleh menjalankan aplikasi kami sekali lagi (mulakan semula pelayan atau gunakan semula ia sekali lagi—apa sahaja yang anda suka) dan pastikan halaman utama dipaparkan, tiada apa-apa yang pecah dan peralihan berlaku apabila kami mengklik butang (walaupun kami mendapat ralat sekali lagi). Ngomong-ngomong, sedangkan sebelum ini kita mendapat ralat 404, kini kita mendapat 405. Ini bermakna pemetaan berfungsi dan servlet ditemui, tetapi mereka tidak mempunyai kaedah yang sesuai untuk mengendalikan permintaan itu.

Penyimpangan pendek: apa yang berlaku "di bawah tudung"?

Anda mungkin sudah memikirkan cara aplikasi kami berfungsi dalam Tomcat. Apa yang berlaku di sana? Dan di manakah kaedah utama()? Sebaik sahaja anda pergi ke localhost:8080 dalam penyemak imbas anda, penyemak imbas menghantar permintaan ke alamat ini menggunakan protokol HTTP. Saya harap anda sudah sedar bahawa terdapat pelbagai jenis permintaan, dan yang paling popular ialah GET dan POST. Setiap permintaan harus dijawab. Permintaan GET dijangka menerima respons kod HTML sedia untuk digunakan, dikembalikan kepada penyemak imbas. Penyemak imbas kemudian menggantikan kod semua huruf, butang dan borang yang cantik. Permintaan POST adalah sedikit lebih menarik, kerana ia juga membawa beberapa maklumat. Sebagai contoh, katakan anda memasukkan bukti kelayakan dalam borang pendaftaran atau log masuk di tapak web dan klik "Hantar". Ini menyebabkan permintaan POST dengan maklumat peribadi anda dihantar ke pelayan. Pelayan menerima maklumat ini, memprosesnya dan mengembalikan beberapa respons (contohnya, halaman HTML dengan profil anda). Perbezaan utama antara mereka ialah permintaan GET hanya digunakan untuk mendapatkan data daripada pelayan, manakala permintaan POST membawa beberapa maklumat (dan data pada pelayan boleh berubah). Sebagai contoh, apabila anda memuat naik gambar anda ke pelayan, ia dibawa ke sana dalam permintaan POST dan pelayan menambahkannya ke pangkalan data, iaitu perubahan berlaku. Sekarang kembali ke Tomcat. Apabila ia menerima permintaan daripada pelanggan, ia melihat alamat. Ia menyemak sama ada terdapat servlet yang sesuai untuk memproses permintaan untuk alamat tersebut (atau sumber yang tersedia yang boleh dikembalikan dengan segera). Jika ia tidak menemui sesuatu untuk dikembalikan, kemudian ia bertindak balas dengan ralat 404 dan bukannya halaman HTML. Tetapi jika ia menemui servlet yang sesuai "duduk" di alamat itu, maka ia melihat jenis permintaan (GET, POST, atau sesuatu yang lain) dan meminta servlet jika ia mempunyai kaedah yang boleh mengendalikan jenis pertanyaan ini. Jika servlet mengatakan ia tidak tahu bagaimana untuk mengendalikan jenis ini, makaTomcat mengembalikan kod 405. Dan inilah yang berlaku dalam projek kami. Tetapi jika servlet yang sesuai ditemui, dan ia mempunyai kaedah yang sesuai, maka Tomcat mencipta objek servlet, memulakannya pada benang baru(yang membolehkan ia berjalan sendiri), dan Tomcat meneruskan kerjanya sendiri, menerima dan menghantar permintaan. Selain itu, Tomcat mencipta dua lagi objek: HttpServletRequest (yang saya panggil "permintaan" secara ringkasnya), dan HttpServletResponse (yang saya panggil "respons"). Ia meletakkan semua data yang diterima daripada permintaan pelanggan ke dalam objek pertama, jadi semua data itu boleh diekstrak daripadanya. Dan kemudian selepas semua ini, ia menyerahkan kedua-dua objek ini kepada kaedah servlet yang sesuai yang dimulakan pada benang yang berasingan. Sebaik sahaja servlet menyelesaikan kerjanya dan mempunyai respons yang sedia untuk dihantar kepada pelanggan, ia mengibarkan bendera di Tomcat, mengatakan "Saya sudah selesai. Semuanya sudah sedia". Tomcat menerima respons dan menghantarnya kepada pelanggan. Ini membolehkan Tomcat menerima permintaan dan menghantar respons, tanpa terganggu, dan semua kerja dilakukan oleh servlet yang berjalan pada benang yang berasingan. Ini bermakna apabila kita menulis kod servlet kita menentukan kerja yang akan dilakukan. Dan anda boleh memikirkan kaedah main() sebagai terletak di dalam Tomcat itu sendiri (ya, ia ditulis dalam Java), dan apabila kami "melancarkan" Tomcat, kaedah main() dimulakan. Mencipta aplikasi web mudah menggunakan servlet dan JSP (bahagian 1) - 2

Gunakan servlet untuk menangkap kaedah GET dan menghantar respons yang sangat mudah

Pada masa ini, servlet kami tidak mempunyai kaedah yang sesuai (GET), jadi Tomcat mengembalikan ralat 405. Mari cipta mereka! Kelas HttpServlet, yang kami warisi oleh servlet kami, mengisytiharkan pelbagai kaedah. Untuk memberikan kod khusus kepada kaedah, kami hanya mengatasinya. Dalam kes ini, kita perlu mengatasi doGet()kaedah dalam kedua-dua servlet.

@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {

}
Seperti yang anda lihat, kaedah ini mengambil dua hujah: req (permintaan) dan resp (tindak balas). Ini adalah objek yang dicipta dan diisi oleh Tomcat untuk kita apabila ia memanggil kaedah yang sesuai dalam servlet. Untuk memulakan, kami akan membuat respons yang paling mudah. Untuk melakukan ini, kami akan mengambil objek resp dan mendapatkan objek PrintWriter daripadanya. Objek jenis ini digunakan untuk menyusun respons. Kami akan menggunakannya untuk mengeluarkan rentetan ringkas.

@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    PrintWriter writer = resp.getWriter();
    writer.println("GET method from AddServlet");
}
Kami akan melakukan sesuatu yang serupa dalam ListServlet, dan kemudian kami akan memulakan semula pelayan kami. Seperti yang anda lihat, semuanya berfungsi! Apabila anda mengklik pada butang, anda mendapat halaman dengan teks yang kami "tulis" dengan PrintWriter. Tetapi fail JSP yang kami sediakan untuk menjana halaman dengan respons tidak digunakan. Itu semata-mata kerana mereka tidak pernah dilaksanakan. Servlet kami mencipta respons itu sendiri dan selesai berjalan, memberi isyarat kepada Tomcat bahawa ia bersedia untuk bertindak balas kepada pelanggan. Tomcat hanya mengambil respons dan menghantarnya semula kepada pelanggan. Mari kita lulus kawalan daripada servlet kepada fail JSP. Kami akan menukar kod kaedah kami seperti berikut:
  • kami memperoleh objek penghantar permintaan daripada objek permintaan, dan memberikannya alamat halaman JSP yang kami ingin pindahkan kawalan;
  • kami menggunakan objek ini untuk memindahkan kawalan ke halaman JSP yang ditentukan, tidak lupa untuk menghantar objek permintaan dan respons yang kami terima daripada Tomcat.

@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    RequestDispatcher requestDispatcher = req.getRequestDispatcher("views/add.jsp");
    requestDispatcher.forward(req, resp);
}
Dalam teg badan halaman JSP, anda boleh menambah sesuatu supaya kami dapat melihat dengan jelas halaman mana yang dipaparkan. Sebaik sahaja anda melakukannya, mulakan semula pelayan dan semak. Kami mengklik butang pada halaman utama dan halaman terbuka, yang bermaksud permintaan sedang dihantar ke servlet. Kemudian kawalan dihantar ke halaman JSP, yang kini diberikan. Itu sahaja buat masa ini. Dalam bahagian seterusnya artikel ini, kami akan mengusahakan kefungsian aplikasi kami.
Komen
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION