2013-07-09 14 views
7

में नियंत्रक का परीक्षण कैसे करूं कहूं कि मुझे दो पैरामीटर प्राप्त करने वाली क्रिया के साथ नियंत्रक मिला है।मैं प्ले फ्रेमवर्क 2 स्कैला

यह एक टेम्पलेट

परिणाम ठीक करने के लिए पारित किया और दिया जाता है करने के लिए दो सेवाओं, प्रत्येक पैरामीटर के साथ एक, सेवाओं दोनों वापसी तार

उन तार में से प्रत्येक के तर्कों के रूप पारित कर रहे हैं invokes।

मैं एक साधारण इकाई परीक्षण सुनिश्चित करता है कि लिखना चाहते हैं: 1 - सही सेवाओं सही पैरामीटर 2 के साथ लागू कर रहे हैं - सेवाओं से वापसी मान टेम्पलेट का सही विशेषताओं को पास किया जाता

क्या ऐसा करने का सबसे अच्छा तरीका है?

+0

क्यों नहीं उपयोग करने के लिए ScalaCheck/ScalaTest/Specs2 0? विशेष रूप से, कैसे आप एक परीक्षण लेखक है – 4lex1v

+0

सेवा और टेम्पलेट के लिए कॉल करने के लिए कॉल अवरोधन करने specs2.0 का उपयोग कर? उदाहरण मैं एक पूरी (एकीकृत) –

उत्तर

2

Specs2 के साथ मॉकिटो का उपयोग करके, मैं उनकी विधि कॉल को सत्यापित करने के लिए सेवाओं का मज़ाक उड़ाता हूं।

मेरा नियंत्रक वसंत द्वारा तत्काल है। इससे मुझे object के बजाय class के रूप में इलाज करने की अनुमति मिलती है। =>controller टेस्ट करने योग्य बनाने के लिए आवश्यक है। यहाँ एक उदाहरण:

@Controller 
class MyController @Autowired()(val myServices: MyServices) extends Controller 

नियंत्रकों के लिए स्प्रिंग सक्षम करने के लिए, आप Play के रूप में, एक Global वस्तु को परिभाषित करने के लिए है! दस्तावेज बताते हैं:

object Global extends GlobalSettings { 

    val context = new ClassPathXmlApplicationContext("application-context.xml") 

    override def getControllerInstance[A](controllerClass: Class[A]): A = { 
    context.getBean(controllerClass) 
    } 
} 

मेरा यूनिट परीक्षण वसंत की आवश्यकता नहीं है; मैं बस कन्स्ट्रक्टर को सहयोगी (मॉक्स) पास करता हूं।

हालांकि, प्रस्तुत टेम्पलेट से संबंधित, मैं केवल परिणाम के प्रकार (ठीक है, BadRequest, पुनर्निर्देशन आदि) के लिए परीक्षण करता हूं। दरअसल, मैंने देखा कि मेरे परीक्षण को पूरे यूनिट परीक्षण के साथ विवरण में पूरे प्रस्तुत किए गए टेम्पलेट को विवरण (इसे भेजे गए पैरामीटर आदि) को स्कैन करने में आसान नहीं है।

इस प्रकार, सही टेम्पलेट को सही तर्क के साथ बुलाया जाने के लिए, मुझे पूरा स्वीकार्य परिणाम स्कैन करने के लिए, यदि आप चाहें तो सेलेनियम या एक संभावित कार्यात्मक परीक्षण चलाने वाले मेरे स्वीकृति परीक्षणों पर भरोसा करते हैं।

2 - सेवाओं से वापसी मान टेम्पलेट

यह that..How के लिए जाँच करने के लिए बहुत आसान है की सही विशेषताओं के लिए पारित कर रहे हैं? संकलक पर भरोसा करके! उदाहरण के लिए सरल प्राइमेटिव्स के बजाय अपने टेम्पलेट में कुछ कस्टम प्रकारों को पास करना पसंद करें: phone: String बन जाएगा: phone: Phone। (एक साधारण मूल्य वस्तु)। इसलिए, आपके टेम्पलेट (यूनिट परीक्षण या वास्तविक उत्पादन कोड में) में गैर-अपेक्षित क्रम में विशेषताओं को पारित करने का कोई डर नहीं है। कंपाइलर वास्तव में चेतावनी देगा।

यहां specs2: का उपयोग करके मेरे यूनिट परीक्षण (सरलीकृत) में से एक का उदाहरण है (आप एक रैपर के उपयोग को नोट करेंगे: WithFreshMocks)। यह case class परीक्षण के बाद परीक्षण के सभी चर (इस मामले में मोजे) को रीफ्रेश करने की अनुमति देगा। इस प्रकार मैक्स को रीसेट करने का एक अच्छा तरीका है।

सेवा दी:

object Application extends ApplicationController 
        with ServiceImpl { 
    def template = views.html.index.apply 
} 

trait ApplicationController extends Controller 
          with Service { 
    def template: (String) => play.api.templates.Html 

    def index = Action { 
    Ok(template("controller got:" + indexMessage)) 
    } 
} 

और:

trait Service { 
    def indexMessage : String 
} 

trait ServiceImpl { 
    def indexMessage = { 
    "Hello world" 
    } 
} 

फिर नियंत्रक की तरह लग रहा

class MyControllerSpec extends Specification with Mockito { 

     def is = 
     "listAllCars should retrieve all cars" ! WithFreshMocks().listAllCarsShouldRetrieveAllCars 

     case class WithFreshMocks() { 

     val myServicesMock = mock[MyServices] 
     val myController = new MyController(myServicesMock) 

     def listAllCarsShouldRetrieveAllCars = { 
      val FakeGetRequest = FakeRequest() //fakeRequest needed by controller 
      mockListAllCarsAsReturningSomeCars() 
      val result = myController.listAllCars(FakeGetRequest).asInstanceOf[PlainResult] //passing fakeRequest to simulate a true request 
      assertOkResult(result). 
      and(there was one(myServicesMock).listAllCars()) //verify that there is one and only one call of listAllCars. If listAllCars would take any parameters that you expected to be called, you could have precise them. 
     } 

     private def mockListAllCarsAsReturningSomeCars() { 
      myServicesMock.listAllCars() returns List[Cars](Car("ferrari"), Car("porsche")) 
     } 

     private def assertOkResult(result: PlainResult) = result.header.status must_== 200 

     } 
+1

मैं एक समाधान है कि मुझे मेरे टेम्पलेट उपहास करने के लिए अनुमति नहीं है के साथ आया के रूप में आवेदन का परीक्षण को देखने के लिए सक्षम किया गया है, लेकिन मैं प्रकार प्रणाली का उपयोग कर परीक्षण त्रुटियों जब संकलक त्रुटियों के बजाय प्राप्त करने का अनुमोदन गलत तर्क का प्रयोग –

2

तो, मैं एक केक पैटर्न और mockito आधारित समाधान के साथ आया था परीक्षण इस तरह दिखता है:

class ApplicationControllerSpec extends Specification with Mockito { 
    "cake ApplicationController" should { 
     "return OK with the results of the service invocation" in { 
     val expectedMessage = "Test Message" 
     val m = mock[(String) => play.api.templates.Html] 

     object ApplicationControllerSpec extends ApplicationController { 
      def indexMessage = expectedMessage 
      def template = m 
     } 

     val response = ApplicationControllerSpec.index(FakeRequest()) 

     status(response) must equalTo(OK) 
     there was one(m).apply(Matchers.eq("controller got:" + expectedMessage)) 
     } 
    } 
} 

मैं मुसीबत Mockito काम कर रही का एक बहुत था।
यह एक अतिरिक्त निर्भरता की आवश्यकता है और मैं बाहर काम कर रहा है कि कैसे स्केला में matchers उपयोग करने के लिए मुसीबत का एक बहुत कुछ था

अंत में मुझे लगता है कि इसके बाद के संस्करण जवाब बेहतर है (मैं जावा में इसका उपयोग करने के लिए काफी आरामदायक हूँ), स्ट्रिंग का उपयोग कर से बचने और अन्य आदिम प्रकार जहां आप उन्हें कार्य विशिष्ट प्रकारों में लपेट सकते हैं, तो आपको कंपाइलर चेतावनियां मिलती हैं।

इसके अलावा, मैं आम तौर पर की तरह काम करने से बचने "नियंत्रक मिला:" होगा नियंत्रक में लगाकर।

तो मैं पुष्टि कर सकते हैं कि यह माध्यम से चला गया, असली दुनिया है कि कुछ अन्य घटक द्वारा किया जाना चाहिए में यह इस मामले में वहाँ (नियंत्रक IMO पाइपलाइन के लिए बस कर रहे हैं)

+0

प्ले 2.3.8 के साथ काम नहीं करता है – zengr

संबंधित मुद्दे