ในอาชีพที่ผ่านมาของฉันฉันมักจะพบว่าบางคนไม่ได้เขียนรหัสทดสอบและเหตุผลที่พวกเขาอ้างว่าไม่เขียนก็คือพวกเขาไม่สามารถเขียนกรณีทดสอบที่ครอบคลุมหลายโมดูลที่แตกต่างกัน ฉันเชื่อว่าพวกเขาส่วนใหญ่ขาดวิธีการทางเทคนิคที่ง่ายต่อการเป็นผู้เชี่ยวชาญหรือไม่มีเวลาคิดออก ท้ายที่สุดจะมีแรงกดดันต่าง ๆ เช่นความคืบหน้าในที่ทำงาน เนื่องจากฉันไม่ทราบวิธีการทดสอบฉันมักจะเพิกเฉยต่อการทดสอบการรวมและปัญหาที่เกิดขึ้นคือการได้รับซอฟต์แวร์ที่แย่ลงมีข้อบกพร่องมากขึ้นเรื่อย ๆ และลูกค้าที่ผิดหวังมากขึ้น ดังนั้นฉันต้องการแบ่งปันประสบการณ์ส่วนตัวเพื่อเปิดเผยความลึกลับของการทดสอบการรวม
วิธีการรวมการทดสอบโครงการที่ใช้สปริง <br /> โดยใช้เครื่องมือ: Spring, Junit, Mockito
ลองนึกภาพว่ามีโครงการฤดูใบไม้ผลิที่รวมบริการภายนอกบางอย่างเช่นบริการเว็บธนาคารบางแห่ง จากนั้นปัญหาที่พบเมื่อเขียนกรณีทดสอบสำหรับโครงการนี้และทำการทดสอบเหล่านี้ในระบบการรวมอย่างต่อเนื่องนั้นเหมือนกัน:
1. จะมีการทำธุรกรรมในการทดสอบแต่ละครั้งและการทำธุรกรรมแต่ละรายการต้องใช้ค่าใช้จ่ายทางการเงินซึ่งลูกค้าจะได้รับผลกระทบในที่สุด
2. คำขอที่มากเกินไปที่ออกในระหว่างการทดสอบอาจได้รับการพิจารณาว่าเป็นอันตรายซึ่งอาจทำให้บัญชีในธนาคารถูกบล็อกโดยผลของการทดสอบล้มเหลว;
3. เมื่อทำการทดสอบโดยใช้สภาพแวดล้อมที่ไม่ใช่การผลิตผลการทดสอบจะไม่น่าเชื่อถือมาก ในทำนองเดียวกันผลที่ตามมาคือการทดสอบล้มเหลว
โดยปกติเมื่อคุณทดสอบคลาสเดียวปัญหาง่ายต่อการแก้ไขเพราะคุณสามารถทำให้บริการภายนอกบางอย่างสำหรับการโทร แต่เมื่อทำการทดสอบกระบวนการทางธุรกิจขนาดใหญ่ทั้งหมดหมายความว่าคุณต้องทดสอบส่วนประกอบหลายอย่างและในเวลานี้คุณต้องรวมส่วนประกอบเหล่านี้ไว้ในคอนเทนเนอร์ฤดูใบไม้ผลิเพื่อการจัดการ โชคดีที่ฤดูใบไม้ผลิรวมถึงกรอบการทดสอบที่ยอดเยี่ยมมากที่ช่วยให้คุณสามารถฉีดถั่วจากไฟล์การกำหนดค่าสภาพแวดล้อมการผลิตลงในสภาพแวดล้อมการทดสอบ แต่สำหรับผู้ที่เรียกว่าบริการภายนอกเราจำเป็นต้องเขียนการติดตั้งจำลองด้วยตนเอง ปฏิกิริยาแรกของคนธรรมดาอาจจะกลับมาใหม่ (แก้ไข) ถั่วที่ฉีดโดยฤดูใบไม้ผลิในระหว่างขั้นตอนการตั้งค่าของการทดสอบ แต่วิธีนี้จะต้องพิจารณาอย่างรอบคอบ
คำเตือน: ด้วยวิธีนี้รหัสทดสอบของคุณจะแบ่งพฤติกรรมของคอนเทนเนอร์ดังนั้นจึงไม่มีการรับประกันว่ามันจะเหมือนกับผลการทดสอบของคุณในสภาพแวดล้อมจริง
ในความเป็นจริงแทนที่จะใช้คลาสเยาะเย้ยก่อนจากนั้นจึงนำกลับมาใช้ใหม่เป็นถั่วที่ต้องการเราสามารถให้ฤดูใบไม้ผลิช่วยเราฉีดคลาสเยาะเย้ยตั้งแต่ต้น มาสาธิตด้วยรหัส
โครงการตัวอย่างมีคลาสที่เรียกว่า Bankservice ซึ่งเป็นตัวแทนของการโทรไปยังบริการภายนอกและคลาสที่เรียกว่า UserGalanceservice ซึ่งเรียกว่า BankService Usergalanceservice ถูกนำมาใช้ง่ายมากเพียงเพื่อให้การแปลงยอดคงเหลือจากสตริงเป็นสองเท่า
รหัสแหล่งที่มาของ Bankservice.java:
อินเตอร์เฟสสาธารณะ BankService {String getBalanceMail (อีเมลสตริง);} ซอร์สโค้ดของ BankserviceImpl.java:
ระดับสาธารณะ BankServiceImpl ใช้ BankService {@Override String สาธารณะ getBalanceByEmail (อีเมลสตริง) {โยน unsupportedOperationException ใหม่ ("การดำเนินการล้มเหลวเนื่องจากข้อยกเว้นภายนอก"); - ซอร์สโค้ดของ userbalanceservice.java:
Interface UserBalanceservice {double getAccountBalance (อีเมลสตริง);} ซอร์สโค้ดของผู้ใช้ useranceserviceimpl.java:
ผู้ใช้ระดับสาธารณะ useranceserviceimpl ดำเนินการ userbalanceservice {@autowired Bankservice Bankservice; @Override สาธารณะ double getAccountBalance (อีเมลสตริง) {return double.valueof (bankservice.getBalanceByeMail (อีเมล)); - จากนั้นก็มีไฟล์การกำหนดค่า XML ของ Spring เพิ่มการประกาศถั่วที่จำเป็น
ซอร์สโค้ดของ ApplicationContext.xml:
<? xml version = "1.0" การเข้ารหัส = "utf-8"?> <beans xmlns = "http://www.springframework.org/schema/beans" xmlns: xsi = "http://ww.w3.org/2001/xml XSI: schemalocation = "http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> <bean id = "Bankservice"/>
นี่คือซอร์สโค้ดของคลาสทดสอบ useranceserviceimpltest.java:
@runwith (springjunit4classrunner.class) @contextconfiguration (locations = "classpath: /springtest/springockito/applicationcontext.xml") คลาสสาธารณะ userveserviceimplprofileTest @autowired Bankservice Bankservice; @Test โมฆะสาธารณะควรได้รับการแก้ไข () {Double Balance = UserBalanceservice.getAccountBalance ("[email protected]"); assertequals (ยอดคงเหลือ, double.valueof (123.45d)); - ตามที่เราคาดไว้วิธีการทดสอบจะรายงานข้อยกเว้นที่ไม่ได้รับการยกเว้น วัตถุประสงค์ปัจจุบันของเราคือการแทนที่ BankService ด้วยการใช้งานการจำลองของเรา มันก็โอเคที่จะใช้ mockito โดยตรงเพื่อสร้างถั่วจากโรงงาน แต่มีตัวเลือกที่ดีกว่าใช้ Framework Springockito คุณสามารถมีความคิดคร่าวๆก่อนดำเนินการต่อ
คำถามที่เหลือเป็นเรื่องง่าย: วิธีการฉีดสปริงลงในถั่วจำลองแทนถั่วจริงไม่มีวิธีอื่นก่อนฤดูใบไม้ผลิ 3.1 ยกเว้นเพื่อสร้างไฟล์การกำหนดค่า XML ใหม่ แต่เนื่องจากฤดูใบไม้ผลิแนะนำนิยามโปรไฟล์ของถั่วเราจึงมีโซลูชันที่สง่างามมากขึ้นแม้ว่าวิธีนี้จะต้องใช้ไฟล์การกำหนดค่า XML เพิ่มเติมสำหรับการทดสอบโดยเฉพาะ นี่คือรหัสสำหรับการกำหนดค่าไฟล์ testapplicationContext.xml ที่ใช้ในการทดสอบ:
<? xml version = "1.0" การเข้ารหัส = "utf-8"?> <beans xmlns = "http://www.springframework.org/schema/beans" xmlns: xsi = "http://ww.w3.org/2001/xml xmlns: mockito = "http://www.mockito.org/spring/mockito" xsi: schemalocation = "http://www.springframework.org/schema/beans http:/www.springframework http://www.mockito.org/spring/mockito https://bitbucket.org/kubek2k/springockito/raw/tip/springockito/src/main/resources/spring/mockito.xsd Resource = "classpath: /springtest/springockito/applicationcontext.xml"/> <beans profile = "springtest"> <mockito: mock id = "bankservice"/> </epeans> </epeans>
ซอร์สโค้ดของคลาสทดสอบ useranceserviceImplProfileTest.java หลังจากทำการดัดแปลงที่สอดคล้องกัน:
@runwith (springjunit4classrunner.class) @contextconfiguration (locations = "classpath: /springtest/springockito/testapplicationcontext.xml")@activeprofiles (profiles = {"Springtest"}) ผู้ใช้ระดับสาธารณะ @autowired Bankservice Bankservice; @Before โมฆะสาธารณะการตั้งค่า () พ่นข้อยกเว้น {mockito.when (bankservice.getBalanceByeMail ("[email protected]")). THENRETURN (String.ValueOf (123.45D)); } @Test โมฆะสาธารณะควรได้รับการแก้ไข BALANCE () {Double Balance = UserBalanceservice.getAccountBalance ("[email protected]"); assertequals (ยอดคงเหลือ, double.valueof (123.45d)); - คุณอาจสังเกตเห็นว่าในวิธีการตั้งค่าเรากำหนดพฤติกรรมจำลองและเพิ่มคำอธิบายประกอบ @profile ลงในชั้นเรียน คำอธิบายประกอบนี้เปิดใช้งานโปรไฟล์ที่เรียกว่า Springtest ดังนั้นถั่วจำลองโดยใช้ Springockito สามารถฉีดได้โดยอัตโนมัติทุกที่ที่ต้องการ ผลการดำเนินการของการทดสอบนี้จะประสบความสำเร็จเนื่องจากฤดูใบไม้ผลิฉีดเวอร์ชันที่จำลองโดย Springockito ไม่ใช่เวอร์ชันที่ประกาศใน ApplicationContext.xml
ดำเนินการต่อเพื่อเพิ่มประสิทธิภาพการทดสอบของเรา
หากเราสามารถแก้ไขปัญหานี้ต่อไปบทความนี้จะไม่มีข้อบกพร่อง Springockito เสนอชื่ออื่นที่เรียกว่า
กรอบ คำอธิบายประกอบ Springockito ซึ่งช่วยให้เราสามารถใช้คำอธิบายประกอบในคลาสทดสอบเพื่อฉีดคลาสเยาะเย้ย ก่อนที่คุณจะอ่านต่อไปควรไปที่เว็บไซต์เพื่อดู ตกลงนี่คือรหัสทดสอบที่แก้ไขแล้ว
ซอร์สโค้ดของผู้ใช้งาน ServiceImplannotationTest.java: @runwith (springjunit4classrunner.class) @contextconfiguration (loader = springockitocontextloader.class, location = "classpath: /springtest/springockiTo/applicationcontext ผู้ใช้บริการผู้ใช้บริการผู้ใช้; @autowired @replacewithmock Bankservice Bankservice; @Before โมฆะสาธารณะการตั้งค่า () พ่นข้อยกเว้น {mockito.when (bankservice.getBalanceByeMail ("[email protected]")). THENRETURN (String.ValueOf (valueof (123.45D))); } @Test โมฆะสาธารณะควรได้รับการแก้ไข BALANCE () {Double Balance = UserBalanceservice.getAccountBalance ("[email protected]"); assertequals (ยอดคงเหลือ, ค่าของ (123.45d)); - โปรดทราบว่าไม่มีไฟล์การกำหนดค่า XML ที่เพิ่งเปิดตัวใหม่ที่นี่ แต่ ApplicationContext.xml ของสภาพแวดล้อมที่เป็นทางการถูกใช้โดยตรง เราใช้คำอธิบายประกอบ @replacewithmock เพื่อทำเครื่องหมายถั่วประเภท Bankservice จากนั้นกำหนดพฤติกรรมของคลาสจำลองในวิธีการตั้งค่า
postscript
โครงการ Springockito-Annotations มีข้อได้เปรียบอย่างมากนั่นคือมันสร้างรหัสทดสอบของเราเกี่ยวกับการครอบคลุมการพึ่งพาเพื่อให้เราไม่จำเป็นต้องกำหนดไฟล์การกำหนดค่า XML เพิ่มเติมหรือแก้ไขไฟล์การกำหนดค่าของสภาพแวดล้อมการผลิตสำหรับการทดสอบ หากไม่ได้ใช้คำอธิบายประกอบ Springockito เราไม่มีทางเลือกนอกจากกำหนดไฟล์การกำหนดค่า XML เพิ่มเติม ดังนั้นฉันขอแนะนำอย่างยิ่งให้คุณใช้ Springockito-Annotations ในการทดสอบการรวมของคุณเพื่อให้คุณสามารถลดผลกระทบของกรณีทดสอบของคุณในรหัสการผลิตของคุณและยังลบภาระของการบำรุงรักษาไฟล์การกำหนดค่า XML เพิ่มเติม
postscript
การเขียนการทดสอบการรวมสำหรับโครงการฤดูใบไม้ผลินั้นง่ายกว่ามาก รหัสในบทความหมายถึง GitHub ของฉันเอง
ลิงค์การแปล: http://www.codeceo.com/article/spring-test-is-easy.html
ภาษาอังกฤษต้นฉบับ: ทดสอบฉันถ้าคุณทำได้ #1 (Framework Spring)
นักแปล: Sandbox Wang, เครือข่ายการเข้ารหัส
ข้างต้นเป็นเนื้อหาทั้งหมดของบทความนี้ ฉันหวังว่ามันจะเป็นประโยชน์ต่อการเรียนรู้ของทุกคนและฉันหวังว่าทุกคนจะสนับสนุน wulin.com มากขึ้น