เหตุใดนักพัฒนา Java จึงควรให้โอกาสแก่ Grails

เผยแพร่แล้ว: 2022-03-11

Java มีระบบนิเวศที่เติบโตเต็มที่ตลอดหลายปีของการพัฒนา ทำให้ Java มีแพลตฟอร์มที่น่าเชื่อถือที่สุดแห่งหนึ่ง แต่ยังขาดวิธีการที่จำเป็นในการทำงานให้เสร็จอย่างรวดเร็ว โดยเฉพาะอย่างยิ่งสำหรับสิ่งต่างๆ เช่น เว็บแอปพลิเคชัน ในความพยายามที่จะหลีกเลี่ยงความผิดหวังกับปัญหาประเภทนี้ นักพัฒนามักจะเลือกใช้ภาษาในการนำไปใช้และเฟรมเวิร์กเว็บที่ทันสมัยแทน เช่น Ruby with Ruby on Rails, Python กับ Django และอื่นๆ ซึ่งแตกต่างจาก Java สิ่งเหล่านี้ให้เส้นทางที่คล่องตัวมากขึ้นในการสร้างเว็บแอปพลิเคชัน

เหตุใดนักพัฒนา Java จึงควรให้โอกาสแก่ Grails

นักพัฒนาเว็บ Java: พบกับ Grails และค้นหาสิ่งที่คุณพลาดไป
ทวีต

โชคดีสำหรับนักพัฒนา Java ที่ต้องการสร้างเว็บแอปพลิเคชัน มี วิธีที่ดีกว่าและเกี่ยวข้องกับ Grails ในบทความนี้ เราจะมาดูกันว่า Grails กับ Groovy เป็นทางเลือกที่ใช้งานได้จริงในขอบเขต JVM อย่างไร เราจะมาดูตัวอย่างที่ Grails ดึงดูดใจเราในฐานะนักพัฒนา Java และอาจดึงดูดให้คนอื่นลองดูด้วย

เรื่องราว

ในการเริ่มต้นที่ฉันทำงานให้ เรามีปัญหาตรงนี้ เรามีแอปพลิเคชั่น Spring ซึ่งใช้งานยาก ด้วยขนาดที่ใหญ่ขึ้นเรื่อย ๆ เราจึงพบว่าการปรับโครงสร้างใหม่และเพิ่มฟังก์ชันการทำงานทำให้เราใช้เวลานานกว่าที่ควรจะเป็น เมื่อรวมกับแรงจูงใจอื่นๆ ทำให้เราตัดสินใจเขียนแอปพลิเคชันหลักของเราใหม่ นอกจากนี้เรายังเปิดรับการเปลี่ยนแปลงหรือแทนที่กลุ่มเทคโนโลยีที่มีอยู่ Grails ดูเหมือนจะเป็นตัวเลือกที่ทำงานได้เนื่องจากทำงานใน JVM และสร้างขึ้นจากเทคโนโลยีที่เรารู้อยู่แล้ว มันใช้ภาษาการเขียนโปรแกรม Groovy แต่ในขณะเดียวกันก็อนุญาตให้คุณผสมกับ Java ดังนั้นเราจึงกระโดด

เดินหน้าเต็มกำลัง

สิ่งหนึ่งที่ Grails เชี่ยวชาญมากคือการทำให้ง่ายต่อการเริ่มโครงการใหม่ มันง่ายพอๆ กับการรันคำสั่งที่สร้างโครงสร้างโปรเจ็กต์พร้อมโฟลเดอร์ทั้งหมดที่จำเป็นสำหรับคลาสที่คุณจะเพิ่มในภายหลัง การเพิ่มคลาสโมเดล ตัวควบคุม บริการ และหน้าเว็บนั้นใช้ความพยายามเพียงเล็กน้อยเช่นเดียวกัน สิ่งเดียวที่คุณต้องดูแลคือการตั้งชื่อและวางสิ่งต่างๆ ให้ถูกต้อง ต่างจาก Java ตรงที่ไม่มีโค้ดสำเร็จรูปที่จำเป็นต้องมีเพียงเพราะจำเป็นต้องมี สิ่งนี้เกิดขึ้นได้บางส่วนโดยใช้ Spring และ Hibernate ซึ่งเป็นเสาหลักสองประการของ Grails รวมถึงแนวคิดของการเข้ารหัสตามแบบแผน ในการรันโครงการ Grails มาพร้อมกับ Apache Tomcat เป็นเซิร์ฟเวอร์การพัฒนา สิ่งที่เราต้องทำคือเรียกใช้โครงการใน IDE ของเราและเซิร์ฟเวอร์จะทำงานด้วยโค้ดของเราที่ปรับใช้ นอกจากนี้ Grails' Object Relational Mapping (GORM) กับ Hibernate จะดูแลการสร้างฐานข้อมูลให้เราด้วย ในการใช้ฐานข้อมูลที่มีอยู่ เราต้องกำหนดค่าคุณสมบัติการเชื่อมต่อ JDBC หรือปล่อยให้เป็นค่าเริ่มต้นเพื่อใช้อินสแตนซ์ในหน่วยความจำ เมื่อเซิร์ฟเวอร์ที่มี Grails ทำงานอยู่ (ใช้เวลามากกว่าแอปพลิเคชัน Spring MVC เล็กน้อย) เราสามารถแก้ไขโค้ดและฟังก์ชันการปรับใช้ด่วนจะทำให้เซสชันการดีบักของเราติดตั้งเวอร์ชันล่าสุด คลาสเดียวที่ไม่สามารถโหลดซ้ำด้วยวิธีนี้คือคลาสเอนทิตี

การเติมฐานข้อมูลสามารถทำได้โดยใช้สคริปต์ SQL แต่อาจเป็นเรื่องที่น่าเบื่อหน่าย โปรเจ็กต์ของ Grails ทั้งหมดมีคลาส Bootstrap ซึ่งจะถูกเรียกใช้เมื่อรันแอปพลิเคชันของเรา ในคลาสนี้ เราสามารถจัดเก็บหรือแก้ไขข้อมูลและทำให้เริ่มต้นสถานะแอปพลิเคชันของเราได้ สิ่งนี้พิสูจน์แล้วว่ามีประโยชน์มากสำหรับเรา ดังนั้นเราจึงมีกรณีทดสอบในเวอร์ชันพัฒนาทันที

ในคลาส Bootstrap เรายังสามารถใช้เงื่อนไข “if” เพื่อตรวจสอบประเภทของสภาพแวดล้อม (การพัฒนา การทดสอบ การผลิต ฯลฯ) และแก้ไขข้อมูลตามนั้น

การจัดการข้อมูล

สิ่งหนึ่งที่ดึงดูดความสนใจของเราในทันทีด้วย Grails คือความง่ายในการทำงานกับข้อมูล การอ่านจากฐานข้อมูลเป็นงานที่ต้องทำซ้ำแล้วซ้ำอีก และหลายครั้งก็เป็นเรื่องง่าย เช่นเดียวกับการดึงเอนทิตีตั้งแต่หนึ่งรายการขึ้นไปที่ตรงตามเกณฑ์ที่กำหนดแล้วจึงรวมเข้าด้วยกัน ทำไมไม่ใช้ตัวค้นหาแบบไดนามิกสำหรับสิ่งนั้น? เป็นวิธีการสืบค้นข้อมูลที่มีการสร้างวิธีการแบบไดนามิกในขณะใช้งานจริง สิ่งที่คุณต้องทำคือทำตามแบบแผนการตั้งชื่อ

 def users = User.findAllByLastNameLikeOrAgeGreaterThan('Doe%', 30)

บรรทัดด้านบนจะดึงวัตถุ User ทั้งหมดที่มีนามสกุลขึ้นต้นด้วย “Doe” หรืออายุมากกว่า 30 ใช่ ไม่ใช่กรณีที่ซับซ้อนมาก แต่คุณจะได้รับส่วนสำคัญ

จะเป็นอย่างไรถ้าเราต้องการกรองรายการนี้เพิ่มเติมสำหรับรายการที่มีคุณสมบัติ “failedLogins” มากกว่า 10 แล้วถ้าเราต้องการจัดเรียงตามวันที่สร้างล่ะ? แล้วถ้าเราต้องการรวมชื่อแรกของพวกเขาเข้าด้วยกันหรือค้นหาอายุสูงสุดของผู้ใช้ที่ส่งคืนล่ะ

 users = users.findAll() { it.failedLogins > 10 } users = users.sort { it.dateCreated } def firstNamesString = users.firstName.join(', ') def maximumAge = users.age.max()

ตัวอย่างข้างต้นอาจดูเรียบง่าย แต่แสดงให้เห็นว่า Grails มีประสิทธิภาพเพียงใดในการสืบค้น กรอง และจัดการข้อมูล ใน Java 8 คุณสามารถบรรลุผลลัพธ์ที่คล้ายคลึงกันสำหรับบางกรณีเหล่านี้ แต่จะยังคงต้องการโค้ดมากกว่า Grails

บางครั้งฉันต้องการสร้างความแตกต่าง

ตัวสร้างไดนามิกหรือตัวสร้างอาร์กิวเมนต์ที่มีชื่อเป็นคุณลักษณะที่พวกเราหลายคนต้องการมีใน Java เป็นการดีที่จะกำหนดว่าคอนสตรัคเตอร์ตัวใดที่คลาสบางคลาสอนุญาต แต่ในหลายกรณี คุณเพียงแค่ต้องการตั้งค่าคุณสมบัติบางอย่างและรับอินสแตนซ์สาปแช่ง Groovy เพิ่มคอนสตรัคเตอร์พิเศษสำหรับแต่ละเอนทิตี ซึ่งโดยทั่วไปจะใช้ความสง่างามของแผนที่เป็นอินพุต และตั้งค่าคุณสมบัติด้วยรายการแผนที่

 def Person = new Person(name: 'Batman', age: 57)

แนวทางนี้นำไปสู่โค้ดที่สื่อความหมายได้ชัดเจนกว่ามาก และหลีกเลี่ยงความจำเป็นในโค้ดสำเร็จรูปของคอนสตรัคเตอร์ทั้งหมด

และ BTW นี่คือตัวอย่างบางส่วนของความยอดเยี่ยมและความสง่างามของแผนที่ของ Groovy:

 def emptyMap = [:] def map = [bread:3, milk:5, butter:2] map['bread'] = 4 map.milk = 6

นี่เป็นอีกตัวอย่างหนึ่งของโค้ดที่สั้นและเรียบง่ายแต่ทรงพลัง โดยจะแสดงวิธีการใช้การเริ่มต้นแบบอินไลน์และวิธีจัดการค่าแผนที่ในลักษณะที่คล้ายกับคุณสมบัติของอ็อบเจ็กต์ ไม่จำเป็นต้องเรียกใช้วิธีการ Java แบบดั้งเดิมสำหรับการจัดการขั้นพื้นฐาน เว้นแต่ว่าคุณต้องการจริงๆ

เราต้องการพลังมากกว่านี้!

แน่นอนว่าไม่มีกรอบงานใดที่สามารถทำทุกอย่างได้ แต่เมื่อเราอุดช่องว่าง เราควรดูว่ามีอะไรอีกบ้างที่มีอยู่ก่อนที่จะพยายามใช้โซลูชันของเราเอง ในการขยายคลังแสงของฟังก์ชันที่ใช้ Grails เราสามารถใช้ Grails Plugins การติดตั้งปลั๊กอินทำได้โดยการเพิ่มบรรทัดอื่นในคลาส BuildConfig ที่มีอยู่ในทุกโปรเจ็กต์ของ Grails (การประชุมโค้ดหยุดทำงานอีกครั้ง!)

 compile ':spring-security-core:2.0-RC4'

บรรทัดด้านบนเพิ่มแกนความปลอดภัย Spring ให้กับแอปพลิเคชันของเรา และแทบไม่มีการกำหนดค่าเพิ่มเติมที่จำเป็นในการรวมฟังก์ชันนี้

คล้ายกับการใช้การพึ่งพา Maven (ซึ่งคุณสามารถอ้างอิงได้ในคลาส config เดียวกัน) แต่ปลั๊กอินมักจะเป็นบล็อกขนาดใหญ่กว่าที่มีฟังก์ชันการทำงานทั้งหมด

ที่กล่าวว่าให้ฉันบอกคุณเกี่ยวกับกรณีที่เราต้องจัดการกับ เราจำเป็นต้องใช้การค้นหาที่ครอบคลุมเอนทิตีข้อมูลหลายรายการ Grails มีปลั๊กอิน Elasticsearch ซึ่งใช้งานง่าย ดังที่ได้กล่าวไว้ก่อนหน้านี้ เราต้องการเพียงแค่อ้างอิงปลั๊กอินในไฟล์ปรับแต่งเท่านั้น และเราพร้อมแล้วที่จะไป หากเราต้องการค้นหาเอนทิตีของคลาสใดคลาสหนึ่ง เราเพียงแค่เพิ่มคุณสมบัติ "ค้นหาได้" แบบคงที่ให้กับคลาสนั้น และหากต้องการ เราสามารถจำกัดคุณสมบัติที่จะอนุญาตให้ค้นหาได้

 class User { static searchable = { only = name } String name Double salary }

เป็นโค้ดที่น้อยมาก แต่ภายใต้ประทุน Grails และปลั๊กอิน Elasticsearch จะสร้างดัชนีผู้ใช้ทั้งหมดโดยอัตโนมัติตามชื่อ และทำให้เราสามารถค้นหาด้วยชื่อได้ การโทรค้นหาจริงยังรัดกุมมาก:

 User.search("${params.query}")

ถ้าเราไม่ต้องการ เราจะไม่ต้องแตะดัชนี Lucene ทั้งหมดจะทำโดยอัตโนมัติอย่างน่าอัศจรรย์สำหรับเรา ปลั๊กอินยังมี API สำหรับแสดงผลการค้นหา ซึ่งสามารถเน้นการจับคู่ที่พบในข้อความที่ค้นหา นี่เป็นเพียงตัวอย่างที่ปลั๊กอินสามารถจัดเตรียมชุดฟังก์ชันการทำงานจำนวนมาก ซึ่งจะทำให้เรามีประสิทธิภาพมากขึ้นโดยไม่จำเป็นต้องติดตั้งเอง

เรายังต้องการพลังมากกว่านี้

ปลั๊กอินนั้นยอดเยี่ยม แต่บางครั้งเราไม่ต้องการปลั๊กอินทั้งหมด เราแค่ต้องการบางอย่างเพิ่มเติม คุณจำครั้งสุดท้ายที่คุณต้องการมีวิธีการเพิ่มเติมในคลาส Java ที่มีอยู่ แต่คุณไม่ต้องการ (หรือไม่สามารถ) ขยาย / แทนที่ได้อย่างไร ใน Groovy คุณสามารถเพิ่มเมธอดและคุณสมบัติให้กับคลาสที่มีอยู่ หรือแม้แต่บางอินสแตนซ์ของคลาสเหล่านั้นได้ ตัวอย่างเช่น คุณสามารถเพิ่มวิธีการ formatting ให้กับคลาส java.util.Date ซึ่งยอดเยี่ยมเมื่อคุณต้องการจัดรูปแบบวันที่อย่างสม่ำเสมอและเพียงแค่ไม่ต้องการเขียนคลาส util แบบคงที่หรือกำหนดตัวกรองต่างๆ

 Date.metaClass.formatDate = { delegate.format("dd.MM.yyyy") }

จะเป็นอย่างไรถ้าคุณต้องการจัดเรียงรายชื่อผู้ใช้ตามค่าที่คำนวณได้ และคุณต้องการเพียงกรณีเดียวเท่านั้น (เช่น การเพิ่มวิธีการใหม่ในคลาสผู้ใช้จะทำให้เกิดมลพิษ) คุณสามารถเพิ่มคุณสมบัติในแต่ละอินสแตนซ์เหล่านั้น จากนั้นเพียงแค่จัดเรียงหรือกรองคอลเลกชันตามคุณสมบัตินั้น:

 user.metaClass.computedProp = 312 * 32 * 3

ผู้เขียน Groovy ได้เพิ่มการปรับปรุงมากมายให้กับคลาส Java หลักบางคลาสแล้ว ดังนั้นเราจึงไม่จำเป็นต้องทำ ด้านล่างนี้เป็นตัวอย่างบางส่วน

ใช้ “ลบ” เพื่อลบองค์ประกอบทั้งหมดออกจากคอลเลกชันที่มีอยู่ในคอลเลกชันอื่น

 assert [1, 2, 3, 4, 4, 5] - [2, 4] == [1, 3, 5]

วิธีการเพิ่มเติมสำหรับการจัดการวัตถุ java.util.Date ซึ่งสะดวกหลายครั้ง เช่น การเพิ่ม/ลบวันจากวันที่ หรือการรับ/ตั้งค่าฟิลด์เฉพาะของวันที่โดยไม่ต้องแปลงเป็น Calendar หรือใช้ไลบรารีเพิ่มเติม

 def yesterdayAllMyTroublesSeemedSoFarAway = new Date() - 1 def myAwesomeAnniversaryYear = myAwesomeDate[Calendar.YEAR] + 1 myAwesomeDate.set(year: myAwesomeAnniversaryYear, second: 0)

เมื่อคุณต้องการอธิบายเกี่ยวกับการจัดการวันที่จริงๆ คุณสามารถใช้คลาส TimeCategory ที่เพิ่ม Groovy ได้:

 use (TimeCategory) { println 1.minute.from.now println 10.hours.ago def someDate = new Date() println someDate - 3.months }

ค้อนกับตะปู

จากนั้นก็มี IDE GGTS ที่ใช้ Eclipse และ IntelliJ IDEA ได้รับการตั้งค่าสำหรับการทำงานกับ Grails พวกเขาเข้าใจโครงสร้างโครงการ (และจะช่วยให้คุณนำทางผ่านโฟลเดอร์และทรัพยากร) และมีทางลัดสำหรับคำสั่งที่คุณจะใช้บ่อยที่สุด (เช่น เพิ่มตัวควบคุม เพิ่มหน้า เรียกใช้โครงการ ฯลฯ) ด้วย Grails คุณจะรันคำสั่ง (เพื่อรันโปรเจ็กต์หรือตั้งค่าฟังก์ชันปลั๊กอินใหม่) และคุณจะต้องมีการกำหนดค่าที่แตกต่างกัน ซึ่ง IDE ครอบคลุมด้วย การเติมโค้ดให้สมบูรณ์ทำงานได้ดีในหน้าเทมเพลตเว็บของ Grails ซึ่งคุณมักจะอ้างอิงถึงคอนโทรลเลอร์และการดำเนินการ นอกจากนี้ยังมี IDE อื่นๆ ที่สามารถใช้กับ Grails ได้ เช่น Netbeans, TextMate, Emacs และอื่นๆ

แล้วด้านมืดล่ะ?

เช่นเดียวกับทุกสิ่งทุกอย่างในชีวิต มีข้อแม้สำหรับ Grails ด้วย มีเวทมนตร์มากมายที่ต้องทำภายใต้ประทุนซึ่งมักจะเป็นสิ่งที่ดี แต่บางครั้งผลลัพธ์อาจไม่เป็นอย่างที่คุณคาดหวัง ข้อบกพร่องจะเกิดขึ้นเพียงเพราะไม่ได้ใช้การพิมพ์ (ใช่ ประเภทเป็นตัวเลือกใน Groovy) และไม่ระมัดระวังเพียงพอ และบางทีคุณจะไม่สังเกตเห็นข้อผิดพลาดจนกว่าจะสายเกินไป นอกจากนี้ การเขียนเพียงคำเดียวเพื่อสร้างความประทับใจให้เพื่อนร่วมงานเป็นเรื่องที่น่าดึงดูดใจ และตัวคุณเอง. แต่โค้ดที่ทรงพลังเหล่านี้อาจไม่สามารถอธิบายตนเองได้สำหรับเพื่อนร่วมงานของคุณ หรือแม้แต่ตัวคุณเองในสองสามเดือน นั่นเป็นเหตุผลที่ฉันคิดว่า Grails ต้องการวินัยในการเขียนโปรแกรมมากกว่าเฟรมเวิร์กดั้งเดิมบางตัว

เวลาคือเงิน

การเข้ารหัสไม่ควรใช้เวลานานเพียงเพราะเฟรมเวิร์กปัจจุบันของคุณต้องการ โดยเฉพาะอย่างยิ่งเมื่อมีบริษัทสตาร์ทอัพจำนวนมากขึ้นเรื่อยๆ ในปัจจุบัน สิ่งสำคัญคือต้องให้ความสำคัญกับงานที่สำคัญจริงๆ และมีประสิทธิภาพมากที่สุด เวลาคือเงินและเวลาสู่ตลาดเป็นสิ่งสำคัญ คุณต้องสามารถดำเนินการได้อย่างรวดเร็วและนำโซลูชันไปใช้ก่อนหมดเวลาและคู่แข่งของคุณเอาชนะคุณได้

เพื่อนของฉันที่ทำงานกับ Ruby on Rails หรือ Python/Django บอกฉันมานานแล้วว่าเทคโนโลยีเหล่านั้นเจ๋งแค่ไหน และมันรู้สึกงี่เง่าจริงๆ ที่คิดว่าฉันต้องใช้เวลามากขึ้นใน Java ในการเขียนโค้ดที่เก็บบางอย่างในฐานข้อมูลและแสดงในหน้าเว็บ Grails อาจเป็นคำตอบที่มีประโยชน์ ไม่ใช่ว่าคุณทำไม่ได้กับ Java, Spring MVC และ Hibernate ล้วนๆ คุณสามารถ แอปพลิเคชันของคุณอาจทำงานเร็วขึ้นเล็กน้อย แต่คุณจะทำงานเสร็จเร็วขึ้นด้วย Grails

ที่เกี่ยวข้อง: ทำไมคุณต้องอัปเกรดเป็น Java 8 แล้ว