Mari berbagi arsitektur aplikasi web berbasis Java!
Ada banyak arsitektur berbeda untuk aplikasi web yang akan diimplementasikan menggunakan Java. Jawaban atas pertanyaan ini dapat berfungsi sebagai perpustakaan berbagai desain aplikasi web dengan pro dan kontra mereka. Sementara saya menyadari bahwa jawabannya akan subyektif, mari kita coba untuk seobjektif mungkin dan memotivasi pro dan kontra yang kita daftarkan.
Gunakan level detail yang Anda inginkan untuk menggambarkan arsitektur Anda. Agar jawaban Anda bernilai apa pun, setidaknya Anda harus menggambarkan teknologi dan gagasan utama yang digunakan dalam arsitektur yang Anda gambarkan. Dan yang tak kalah pentingnya, kapan kami harus menggunakan arsitektur Anda?
Saya akan mulai...
Tinjauan arsitektur
Kami menggunakan arsitektur 3-tier berdasarkan pada standar terbuka dari Sun seperti Java EE, Java Persistence API, Servlet dan Java Server Pages.
- Kegigihan
- Bisnis
- Presentasi
Kemungkinan arus komunikasi antar lapisan diwakili oleh:
Persistence <-> Business <-> Presentation
Yang misalnya berarti bahwa lapisan presentasi tidak pernah memanggil atau melakukan operasi kegigihan, itu selalu melakukannya melalui lapisan bisnis. Arsitektur ini dimaksudkan untuk memenuhi permintaan aplikasi web ketersediaan tinggi.
Kegigihan
Melakukan operasi membuat, membaca, memperbarui, dan menghapus ( CRUD ) persistensi. Dalam kasus kami, kami menggunakan ( Java Persistence API ) JPA dan kami saat ini menggunakan Hibernate sebagai penyedia ketekunan kami dan menggunakan EntityManager-nya .
Lapisan ini dibagi menjadi beberapa kelas, di mana setiap kelas berurusan dengan jenis entitas tertentu (yaitu entitas yang terkait dengan keranjang belanja mungkin ditangani oleh kelas persistensi tunggal) dan digunakan oleh satu dan hanya satu manajer .
Selain itu lapisan ini juga menyimpan entitas JPA yang merupakan hal-hal seperti Account
, ShoppingCart
dll.
Bisnis
Semua logika yang terkait dengan fungsionalitas aplikasi web terletak di lapisan ini. Fungsionalitas ini dapat memulai transfer uang untuk pelanggan yang ingin membayar produk secara online menggunakan kartu kreditnya. Bisa juga menciptakan pengguna baru, menghapus pengguna atau menghitung hasil pertempuran dalam game berbasis web.
Lapisan ini dibagi menjadi beberapa kelas dan masing-masing kelas ini dianotasi dengan @Stateless
menjadi Bean Sesi Stateless (SLSB). Setiap SLSB disebut manajer dan misalnya seorang manajer bisa menjadi kelas yang dijelaskan sebagaimana disebut AccountManager
.
Ketika AccountManager
perlu melakukan operasi CRUD, ia membuat panggilan yang sesuai ke instance AccountManagerPersistence
, yang merupakan kelas di lapisan persistensi. Sketsa kasar dari dua metode di AccountManager
dapat:
...
public void makeExpiredAccountsInactive() {
AccountManagerPersistence amp = new AccountManagerPersistence(...)
// Calls persistence layer
List<Account> expiredAccounts = amp.getAllExpiredAccounts();
for(Account account : expiredAccounts) {
this.makeAccountInactive(account)
}
}
public void makeAccountInactive(Account account) {
AccountManagerPersistence amp = new AccountManagerPersistence(...)
account.deactivate();
amp.storeUpdatedAccount(account); // Calls persistence layer
}
Kami menggunakan transaksi manajer kontainer sehingga kami tidak perlu melakukan demarkasi transaksi sendiri. Apa yang pada dasarnya terjadi di bawah kap adalah kami melakukan transaksi ketika memasuki metode SLSB dan melakukan itu (atau mengembalikannya) segera sebelum keluar dari metode. Ini adalah contoh konvensi tentang konfigurasi, tetapi kami belum membutuhkan apa pun kecuali yang standar, Diperlukan, belum.
Inilah cara Tutorial Java EE 5 dari Sun menjelaskan atribut transaksi yang Diperlukan untuk Enterprise JavaBeans (EJB):
Jika klien berjalan dalam transaksi dan memanggil metode perusahaan kacang, metode dijalankan dalam transaksi klien. Jika klien tidak terkait dengan transaksi, wadah memulai transaksi baru sebelum menjalankan metode.
Atribut yang diperlukan adalah atribut transaksi implisit untuk semua metode bean perusahaan yang berjalan dengan demarkasi transaksi yang dikelola oleh kontainer. Anda biasanya tidak menetapkan atribut yang diperlukan kecuali Anda perlu mengganti atribut transaksi lainnya. Karena atribut transaksi bersifat deklaratif, Anda dapat dengan mudah mengubahnya nanti.
Presentasi
Lapisan presentasi kami bertanggung jawab atas ... presentasi! Ini bertanggung jawab untuk antarmuka pengguna dan menunjukkan informasi kepada pengguna dengan membangun halaman HTML dan menerima input pengguna melalui permintaan GET dan POST. Kami saat ini menggunakan kombinasi + Java Server Pages ( JSP ) Servlet lama .
Lapisan memanggil metode di manajer lapisan bisnis untuk melakukan operasi yang diminta oleh pengguna dan untuk menerima informasi untuk ditampilkan di halaman web. Terkadang informasi yang diterima dari lapisan bisnis adalah tipe yang tidak terlalu kompleks seperti String
's dan int
eger, dan di lain waktu entitas JPA .
Pro dan kontra dengan arsitekturnya
Pro
- Memiliki semua yang terkait dengan cara tertentu untuk melakukan kegigihan di lapisan ini hanya berarti kita dapat bertukar dari menggunakan JPA menjadi sesuatu yang lain, tanpa harus menulis ulang apa pun di lapisan bisnis.
- Sangat mudah bagi kita untuk menukar layer presentasi kita menjadi sesuatu yang lain, dan kemungkinan kita akan melakukannya jika kita menemukan sesuatu yang lebih baik.
- Membiarkan wadah EJB mengatur batas-batas transaksi itu bagus.
- Menggunakan Servlet's + JPA mudah (untuk memulai) dan teknologinya banyak digunakan dan diimplementasikan di banyak server.
- Menggunakan Java EE seharusnya memudahkan kita untuk membuat sistem ketersediaan tinggi dengan penyeimbangan beban dan kegagalan . Keduanya kami rasa harus kami miliki.
Cons
- Menggunakan JPA, Anda dapat menyimpan kueri yang sering digunakan sebagai kueri bernama dengan menggunakan
@NamedQuery
anotasi pada kelas entitas JPA. Jika Anda memiliki sebanyak mungkin terkait dengan kegigihan di kelas kegigihan, seperti dalam arsitektur kami, ini akan menyebar lokasi di mana Anda mungkin menemukan pertanyaan untuk menyertakan entitas JPA juga. Akan lebih sulit untuk meninjau operasi kegigihan dan karenanya lebih sulit untuk mempertahankannya. - Kami memiliki entitas JPA sebagai bagian dari lapisan ketekunan kami. Tapi
Account
danShoppingCart
, bukankah itu benar-benar objek bisnis? Hal ini dilakukan dengan cara ini karena Anda harus menyentuh kelas-kelas ini dan mengubahnya menjadi entitas yang JPA tahu cara menanganinya. - Entitas JPA, yang juga merupakan objek bisnis kami, dibuat seperti Data Transfer Objects ( DTO 's), juga dikenal sebagai Value Objects (VO's). Ini menghasilkan model domain anemia karena objek bisnis tidak memiliki logika sendiri kecuali metode accessor. Semua logika dilakukan oleh manajer kami di lapisan bisnis, yang menghasilkan gaya pemrograman yang lebih prosedural. Ini bukan desain berorientasi objek yang bagus, tapi mungkin itu bukan masalah? (Bagaimanapun orientasi objek bukan satu-satunya paradigma pemrograman yang telah memberikan hasil.)
- Menggunakan EJB dan Java EE memperkenalkan sedikit kompleksitas. Dan kita tidak bisa menggunakan Tomcat murni (menambahkan wadah mikro EJB tidak sepenuhnya Tomcat).
- Ada banyak masalah dengan menggunakan Servlet's + JPA. Gunakan Google untuk informasi lebih lanjut tentang masalah ini.
- Karena transaksi ditutup ketika keluar dari lapisan bisnis, kami tidak dapat memuat informasi apa pun dari entitas JPA yang dikonfigurasi untuk dimuat dari basis data ketika diperlukan (menggunakan
fetch=FetchType.LAZY
) dari dalam lapisan presentasi. Ini akan memicu pengecualian. Sebelum mengembalikan entitas yang berisi bidang-bidang semacam ini, kami harus memastikan untuk memanggil pengambil yang relevan. Pilihan lain adalah menggunakan Java Persistence Query Language ( JPQL ) dan melakukan aFETCH JOIN
. Namun kedua opsi ini sedikit rumit.
sumber
Jawaban:
Ok saya akan melakukan yang (lebih pendek):
Kami menggunakan dukungan transaksi Sping, dan memulai transaksi setelah memasuki lapisan layanan, menyebar ke panggilan DAO. Lapisan Layanan memiliki pengetahuan model paling bussines, dan DAO melakukan pekerjaan CRUD yang relatif sederhana.
Beberapa hal permintaan yang lebih rumit ditangani oleh permintaan yang lebih rumit di backend karena alasan kinerja.
Keuntungan menggunakan Spring dalam kasus kami adalah kami dapat memiliki instance yang bergantung pada negara / bahasa, yang berada di belakang kelas Proxy Spring. Berdasarkan pengguna dalam sesi tersebut, implementasi negara / bahasa yang benar digunakan saat melakukan panggilan.
Manajemen transaksi hampir transparan, kembalikan pada pengecualian runtime. Kami menggunakan pengecualian yang tidak dicentang sebanyak mungkin. Kami dulu melakukan pengecekan pengecualian, tetapi dengan diperkenalkannya Spring saya melihat manfaat dari pengecualian yang tidak dicentang, hanya menangani pengecualian jika Anda bisa. Ini menghindari banyak barang "tangkapan / rethrow" atau "melempar" boilerplate.
Maaf ini lebih pendek dari posting Anda, harap Anda menemukan ini menarik ...
sumber
Teknologi Pengembangan Web Berbasis Java Ideal Saat Ini.
Lapisan Web:
HTML + CSS + Ajax + JQuery
RESTFul Pengontrol Web / Tindakan / Lapisan Pemrosesan Permintaan:
Mainkan Kerangka
Logika Bisnis / Lapisan Layanan:
Gunakan Pure Java Code selama mungkin. Satu dapat melakukan perpaduan layanan web di sini.
Lapisan Transformasi Data XML / JSon:
XMLTool (Pencarian Di Google Code), JSoup, Google GSon, XStream, JOOX (Pencarian Di Google Code)
Lapisan Persistensi:
CRUD: JPA atau SienaProject atau QueryDSL / Query Complex: JOOQ, QueryDSL
sumber
Ini 5 sen saya
Presentasi
Android, Angular.JS WebClient, OAUTHv2
API
REST, Jersey (JAX-RS), Jackson (JSON de- / serialisasi), objek DTO (berbeda dari model logika bisnis)
Logika bisnis
Pegas untuk penanganan DI dan Acara. Pendekatan DDD-ish dari objek model. Pekerjaan yang berjalan lebih lama dibebani dengan SQS dalam modul pekerja.
DAO
Model repositori dengan templat JDBC Spring untuk menyimpan Entitas. Redis (JEDIS) untuk Papan, menggunakan Daftar Pesanan. Memcache untuk Token Store.
Basis data
MySQL, Memcached, Redis
sumber
Apa yang kami ikuti dalam proyek kami adalah:
Teknologi ujung depan
API
Logika bisnis
DATA MUSIM SEMI
SPRING data MongoDB
Basis data
Server (Untuk caching)
sumber
Kami masih menggunakan tumpukan Struts-Spring-Hibernate yang biasa.
Untuk aplikasi yang akan datang, kami mencari ke Spring Web Flow + Spring MVC + Hibernate atau Spring + Hibernate + Web Services dengan Flex front end.
Ciri khas arsitektur kami adalah modularisasi. Kami memiliki sejumlah modul, beberapa mulai dengan 3 hingga maksimal 30 tabel dalam database. Sebagian besar modul terdiri dari proyek bisnis dan web. Proyek bisnis memegang logika bisnis dan kegigihan sementara web memiliki logika presentasi.
Pada tingkat logis, ada tiga lapisan: Bisnis, Ketekunan dan Presentasi.
Ketergantungan:
Presentasi tergantung pada Bisnis dan Kegigihan.
Ketekunan tergantung pada Bisnis.
Bisnis tidak bergantung pada lapisan lain.
Sebagian besar proyek bisnis memiliki tiga jenis antarmuka (catatan: bukan GUI, ini adalah lapisan antarmuka java yang terprogram).
Seringkali, 1 diperluas 2. Dengan cara ini, mudah untuk mengganti satu implementasi modul dengan yang lain. Ini membantu kami beradaptasi dengan klien yang berbeda dan mengintegrasikan dengan lebih mudah. Beberapa klien hanya akan membeli modul tertentu dan kami perlu mengintegrasikan fungsionalitas yang sudah mereka miliki. Karena antarmuka dan lapisan implementasi terpisah, mudah untuk meluncurkan implementasi modul ad-hock untuk klien tertentu tanpa mempengaruhi modul dependen. Dan Spring Framework memudahkan untuk menyuntikkan implementasi yang berbeda.
Lapisan bisnis kami didasarkan pada POJO. Satu kecenderungan yang saya amati adalah bahwa POJO ini menyerupai DTO. Kami menderita model domain anemia . Saya tidak yakin mengapa hal ini terjadi tetapi bisa disebabkan oleh kesederhanaan domain masalah dari banyak modul kami, sebagian besar pekerjaannya adalah CRUD atau karena pengembang lebih suka menempatkan logika di tempat lain.
sumber
Berikut adalah satu lagi arsitektur web yang telah saya kerjakan:
Tingkat Presentasi:
Web seluler (HTML5 / CSS3 / Desain responsif)
Spring REST Controllers (Dapat diubah ke JAX-RS)
Tingkat Layanan Bisnis:
Spring @Service (Dapat berubah ke Stateless EJB)
Tingkat Akses Data:
Spring @Repository (Dapat berubah ke Stateless EJB)
Tingkat Sumber Daya:
Entitas Hibernate (JPA) (Dapat berubah ke ORM apa pun)
Anda dapat menemukan informasi lebih lanjut tentang buku yang mengikuti arsitektur ini di sini .
sumber
IMHO, kebanyakan dari kita memiliki penyebut yang sama. Setidaknya di back-end, kami memiliki beberapa bentuk wadah IOC / DI dan kerangka kerja kegigihan. Secara pribadi saya menggunakan Guice dan Mybatis untuk ini. Perbedaannya terletak pada bagaimana kita mengimplementasikan layer view / UI / presentation. Ada 2 opsi utama di sini (mungkin lebih) .. Berbasis tindakan (URL dipetakan ke pengontrol) dan berbasis komponen. Saat ini saya menggunakan lapisan presentasi berbasis komponen (menggunakan gawang). Dengan sempurna meniru lingkungan desktop tempat saya menggunakan komponen dan acara yang bertentangan dengan URL dan pengontrol. Saat ini saya sedang mencari alasan mengapa saya harus bermigrasi ke arsitektur jenis pengontrol URL ini (itulah sebabnya saya berakhir di halaman ini). Mengapa hype tentang arsitektur tenang dan stateless.
Untuk menjawab pertanyaan ini secara singkat: Saya menulis aplikasi web stateful menggunakan kerangka kerja berorientasi komponen di atas wadah Guice IOC dan memasukkan data ke dalam basis data relasional menggunakan Mybatis.
sumber
Sedikit berbeda, dan saya akan mengklaim arsitektur java lebih modular di sini. Kita punya:
Selain di atas, kami memiliki modul perpustakaan bersama yang merupakan penyedia fungsi umum untuk semua layanan.
Penggunaan lapisan yang berbeda memungkinkan kita decoupling penuh dan modularitas yang kita butuhkan. Kami juga dapat sepenuhnya memanfaatkan kekuatan Java EE dan juga Spring. Tidak ada yang mencegah kita menggunakan JSF, misalnya, untuk ujung depan jika diperlukan.
Dibandingkan dengan contoh arsitektur oleh OP, saya pikir ini dapat digambarkan sebagai memiliki empat lapisan utama, bukan tiga, meskipun dengan twist.
sumber
Saya telah mengerjakan proyek yang menggunakan pola manajer yang kaku itu. Secara historis, saya adalah pendukung besar hierarki yang kaku di mana semuanya masuk ke dalam kotak yang rapi. Ketika saya mengalami kemajuan dalam karir saya, saya merasa terpaksa dalam banyak kasus. Saya percaya bahwa mengadopsi pola pikir yang lebih gesit terhadap desain aplikasi mengarah ke produk yang lebih baik. Apa yang saya maksudkan dengan ini menciptakan seperangkat kelas yang memecahkan masalah yang dihadapi. Daripada mengatakan "Apakah Anda membangun manajer untuk ini dan itu?"
Proyek saat ini yang sedang saya kerjakan adalah aplikasi web dengan kombinasi panggilan Spring MVC dan RestEasy JSON / Ajax. Di sisi server yang tertanam dalam pengontrol kami adalah tier data berbasis fasad yang masuk akal dengan JPA / Hibernate untuk akses Database langsung, beberapa akses EJB, dan beberapa panggilan layanan web berbasis SOAP. Mengikat semua ini bersama-sama adalah beberapa kode pengontrol java kustom yang menentukan apa yang harus diserialisasi sebagai JSON dan kembali ke klien.
Kami hampir tidak menghabiskan waktu untuk mencoba membuat beberapa pola yang disatukan alih-alih memilih untuk mengadopsi ide "Worse is Better" dari Unix Design Philosophy. Menjadi yang jauh lebih baik untuk warna di luar garis dan membangun sesuatu yang masuk akal, lebih cepat daripada membangun sesuatu yang mematuhi sekelompok mandat desain yang ketat.
sumber
Komponen dalam Arsitektur Aplikasi Web meliputi:
1: Browser: Interaksi klien
2: Internet
3: Server web
4: Server Aplikasi
5: Server Database
6: Data
sumber