2013-01-23 21 views
12

मेरे पास वेबएपीआई नियंत्रक हैं जो उनके नामों में "एपी" प्रत्यय के साथ समाप्त होते हैं (पूर्व में: छात्र एपीआई नियंत्रक, प्रशिक्षक एपीआई नियंत्रक)। मैं वेबएपीआई नियंत्रकों से अपने एमवीसी नियंत्रकों को आसानी से अंतर करने के लिए ऐसा करता हूं। मैं अपने WebAPI मार्गोंएएसपी.नेट वेब एपी रूटिंग अनुकूलन

http://localhost:50009/api/students/5 और नहीं http://localhost:50009/api/studentsapi/5 के समान दिखाई करना चाहते हैं।

वर्तमान में इस लक्ष्य को हासिल करने के लिए, मैं की तरह के रूप में मैं अपने नियंत्रकों में प्रत्येक विधि के लिए एक मार्ग जोड़ने के लिए

routes.MapHttpRoute(
name: "GetStudents", 
routeTemplate: "api/students/{id}", 
defaults: new { controller = "StudentsApi", id = RouteParameter.Optional }); 

routes.MapHttpRoute(
name: "GetInstructors", 
routeTemplate: "api/instructors/{id}", 
defaults: new { controller = "InstructorsApi", id = RouteParameter.Optional }); 

यह बाहर घूम रहा है बहुत बोझिल हो के लिए मार्गों की स्थापना कर रहा हूँ। मुझे आशा है कि मार्ग टेम्पलेट्स सेट अप करने का एक आसान तरीका होना चाहिए जो मार्गों को संसाधित करते समय स्वचालित रूप से "एपीआई" नियंत्रक नाम को जोड़ता है।

उत्तर

7

मुझे लगता है कि आप जिस एक्स्टेंसिबिलिटी पॉइंट को ढूंढ रहे हैं वह नियंत्रक चयनकर्ता है। आप एक वर्ग बना सकते हैं जो DefaultHttpControllerSelector से प्राप्त होता है और "api" भाग को बाहर करने के लिए GetControllerName को ओवरराइड करता है। फिर आप अपनी सेवा की कॉन्फ़िगरेशन सेवाओं पर इस नियंत्रक चयनकर्ता को पंजीकृत कर सकते हैं।

+0

कुछ ऐसा दिखाई देगा एक अच्छी जगह की जांच के लिए की तरह लगता है। मैं उसे एक शॉट दूंगा और आपको बता दूंगा कि यह कैसे जाता है। – muruge

9

@Youssef Moussaoui की दिशा के बाद मैंने निम्नलिखित कोड लिखने को समाप्त कर दिया जिसने समस्या हल की।

public class ApiControllerSelector : DefaultHttpControllerSelector 
{ 
    public ApiControllerSelector(HttpConfiguration configuration) 
     : base(configuration) 
    { 
    } 

    public override string GetControllerName(HttpRequestMessage request) 
    { 
     if (request == null) 
      throw new ArgumentNullException("request"); 

     IHttpRouteData routeData = request.GetRouteData(); 

     if (routeData == null) 
      return null; 

     // Look up controller in route data 
     object controllerName; 
     routeData.Values.TryGetValue("controller", out controllerName); 

     if (controllerName != null) 
      controllerName += "api"; 

     return (string)controllerName; 
    } 
} 

और जैसा कि

GlobalConfiguration.Configuration.Services.Replace(typeof(IHttpControllerSelector), 
      new ApiControllerSelector(GlobalConfiguration.Configuration)); 
+1

muruge, अगर आप बस बेस कॉल करते हैं तो यह बहुत आसान होगा। GetControllerName और फिर इसे "api" जोड़ें। लेकिन यह सही विचार है। यह देखने के लिए खुशी हुई :) –

+0

मैं सहमत हूं, यह बहुत साफ होगा। मुझ पर हमला नहीं किया। :) – muruge

+0

मुझे कुछ याद आना चाहिए, यह मेरे लिए काम नहीं कर रहा है। मैं अपने नियंत्रक चयनकर्ता को बुला रहा हूं और यह अंत में एपीआई के साथ वापस आ रहा है लेकिन मेरे नियंत्रक को कभी नहीं बुलाया जाता है। –

7

अब जब कि ASP.NET वेब एपीआई 2 बाहर है, वहाँ की तरह है कि आप का सुझाव दिया और अधिक जटिल मार्ग करने के लिए एक बहुत कम बोझिल रास्ता Global.asax में यह रजिस्टर, attribute routing का उपयोग करके।

अपने नियंत्रक के शीर्ष पर सिर्फ निम्न विशेषता जोड़ें:

[RoutePrefix("api/students")] 
public class StudentsApiController : ApiController 
{ 
    ... 
} 

और फिर प्रत्येक एपीआई विधि से पहले:

[Route("{id}"] 
public HttpResponseMessage Get(int id) 
{ 
    ... 
} 

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

+0

इसे अभी भी विशेषता रूटिंग के साथ "नियंत्रक" प्रत्यय की आवश्यकता है। – angularsen

1

muruug के जवाब पर युसुफ की टिप्पणी के बाद इस

public class ApiControllerSelector : DefaultHttpControllerSelector 
{ 
    public ApiControllerSelector (HttpConfiguration configuration) : base(configuration) { } 

    public override string GetControllerName(HttpRequestMessage request) 
    { 
     return base.GetControllerName(request) + "api"; 
    } 
} 
संबंधित मुद्दे