2012-05-08 15 views
5

मैं Watin का उपयोग कर specflow परीक्षण लिख रहा हूँ, जो T4MVC का उपयोग करता है एक Asp.Net MVC आवेदन के लिए।का उपयोग Asp.Net MVC मार्गों (परीक्षण)

मैं टेस्ट मैचों में "जादू स्ट्रिंग" यूआरएल, जो मुझे पसंद नहीं है का उपयोग करते हुए अपने आप को लगता है।

[Given(@"I am on the sign up page")] 
public void GivenIAmOnTheSignUpPage() 
{ 
    string rootUrl = ConfigurationManager.AppSettings["RootUrl"]; 
    string fullUrl = string.Format("{0}/Authentication/Signup",rootUrl); 
    WebBrowser.Current.GoTo(fullUrl); 
} 

मैं बहुत बल्कि मेरी T4MVC कार्रवाई परिणाम का प्रयोग करेंगे जैसे मैं MVC अनुप्रयोग में कुछ इस तरह करते हैं, ...

[Given(@"I am on the sign up page")] 
public void GivenIAmOnTheSignUpPage() 
{ 
    WebBrowser.Current.GoTo(MVC.Authentication.SignUp().ToAbsoluteUrl()); 
} 

मेरे ToAbsoluteUrl एक्सटेंशन विधि

public static class RouteHelper 
{ 
    private static UrlHelper _urlHelper; 
    private static string _rootUrl; 

    public static string ToAbsoluteUrl(this ActionResult result) 
    { 
     EnsureUrlHelperInitialized(); 

     var relativeUrl = _urlHelper.Action(result); 
     return string.Format("{0}/{1}", _rootUrl, relativeUrl); 
    } 

    private static void EnsureUrlHelperInitialized() 
    { 
     if (_urlHelper==null) 
     { 
      _rootUrl = ConfigurationManager.AppSettings["RootUrl"]; 

      var request = new HttpRequest("/", _rootUrl, ""); 
      var response = new HttpResponse(new StringWriter()); 
      var context = new HttpContext(request,response); 
      HttpContext.Current = context; 
      var httpContextBase = new HttpContextWrapper(context); 


      RouteTable.Routes.Clear(); 
      MvcApplication.RegisterRoutes(RouteTable.Routes); 

      var requestContext = new RequestContext(httpContextBase, RouteTable.Routes.GetRouteData(httpContextBase)); 

      _urlHelper = new UrlHelper(requestContext, RouteTable.Routes); 
     } 
    } 
} 

क्या है RequestContext और रूट कोलेक्शन को प्रारंभ करने का सही तरीका ताकि मैं अपना परीक्षण यूआरएल उत्पन्न कर सकूं?

वर्तमान में मैं लाइन var requestContext = new RequestContext(httpContextBase, RouteTable.Routes.GetRouteData(httpContextBase)); पर एक NullReferenceException प्राप्त करते हैं। क्या अनुरोध को नया करने का सही तरीका है?

या यदि कोई एक्शन रिसेट (टी 4 एमवीसी से) लेने के लिए एक बेहतर तरीका है और इसे एक वेब एप के बाहर एक पूर्ण यूआरएल में हल करें, तो यह वास्तव में मैं जो खोज रहा हूं।

+0

स्पेकफ़्लो के साथ आप किस यूनिट टेस्ट लिब का उपयोग कर रहे हैं? MsTest, NUnit, या कुछ और? – danludwig

+0

मैं xUnit का उपयोग कर रहा हूं, क्या इससे कोई फर्क पड़ता है? – Brook

+0

नहीं, मैं सोच रहा था इसलिए मैं अपना जवाब कस्टमाइज़ कर सकता था। मुझे यकीन नहीं है कि xunit समकक्ष [टेस्ट क्लास] और [विधानसभा आरंभ] के लिए क्या हैं, लेकिन कल्पना करें कि यह पता लगाना मुश्किल नहीं है। – danludwig

उत्तर

5
public static class RouteHelper 
{ 
    private static UrlHelper _urlHelper; 
    private static string _rootUrl; 

    static RouteHelper() 
    { 
     var routes = new RouteCollection(); 
     MvcApplication.RegisterRoutes(routes); 
     var req = new HttpRequest(string.Empty, "http://www.site.com", null); 
     var res = new HttpResponse(null); 
     var ctx = new HttpContext(req, res); // do not use HttpContext.Current 
     var requestContext = new RequestContext(new HttpContextWrapper(ctx), 
      new RouteData()); 
     _urlHelper = new UrlHelper(requestContext, routes); 
     _rootUrl = ConfigurationManager.AppSettings["RootUrl"]; 
    } 

    public static string ToAbsoluteUrl(this ActionResult result) 
    { 
     return string.Format("{0}{1}", _rootUrl, _urlHelper.Action(result)); 
    } 
} 

स्थिर निर्माता आपके निजी फ़ील्ड सेट करता है। मैंने स्थिर रूटटेबल का उपयोग करने के बजाय, एक नया रूट चयन का चयन करना चुना। रूट्स संपत्ति, लेकिन आप सक्षम हो सकते हैं।

मैं HttpRequest और HttpResponse बात के लिए कंस्ट्रक्टर्स नहीं लगता। मैं बस अपवाद फेंकने के बिना उन्हें बनाने के लिए कुछ तारों में पारित किया। उन ब्रांडों का उपयोग करें जो एक नया नया HttpContext बनाने के लिए उपयोग करें (xUnit से चलते समय HttpContext.Current का उपयोग न करें)। फिर आप इसे HttpContextBase संदर्भ प्राप्त करने के लिए एक HttpContextWrapper में डाल सकते हैं।

एक नया RequestContext का निर्माण, अपने आधार आवरण और एक नया RouteData उदाहरण में गुजर। UrlHelper बनाने के लिए अपने पिछले रूट चयन के साथ इसका उपयोग करें। ध्यान दें कि इसकी एक्शन विधि "/" के साथ प्रीपेड स्ट्रिंग लौटाएगी, इसलिए आपको इसे हमारे रूट यूआरएल ऐपसेटिंग से बाहर छोड़ देना चाहिए (इसलिए पिछला स्लैश के बिना value = "https://develop.site.com" जैसे कुछ का उपयोग करें)।

इस नोट MVC क्षेत्रों में परिभाषित मार्गों के लिए काम नहीं करेगा। इसके लिए, आपको ग्लोबल असैक्स में RegisterRoutes को कॉल करने के अलावा क्षेत्रों को पंजीकृत करने की आवश्यकता है।

+0

उसने ऐसा किया, धन्यवाद। मैंने इसे टाइप प्रारंभकर्ता के बजाय "सुनिश्चित करें" विधि का उपयोग करने के लिए बदल दिया है, क्योंकि समस्या होने पर वे बहुत अजीब अपवाद फेंकते हैं, और यह देखते हुए कि यह कॉन्फ़िगरेशन से पढ़ रहा है, ऐसा होने की संभावना है। – Brook

+0

आप कितने lifesaver हैं .. मैं इसके लिए घंटों के लिए googled –