Check alle échte Black Friday-deals Ook zo moe van nepaanbiedingen? Wij laten alleen échte deals zien

[ASP.NET] Controller en ApiController combineren

Pagina: 1
Acties:

  • Erwin537
  • Registratie: December 2008
  • Laatst online: 18:25
Beste,

Ik ben bezig met het maken van een prototype voor een webapplicatie framework/Visual Studio template waarbij het AJAX gebeuren al geregeld is. Hiervoor werk ik met REST, met een ApiController met daarin de CRUD acties. Het adres waar de requests naar toe worden gestuurd wil ik automatisch uit de URL halen.

Voorbeeld
Ik heb een test applicatie voor een boeken beheer. De overzicht pagina is te vinden op http://localhost:xxxx/Book/. Een javascript haalt /Book/ uit het adres en zorgt er voor dat AJAX (zoals create en delete) calls automatisch naar /api/Book/ gaan.



Nu heb ik echter het probleem dat de controller voor de gewone index pagina (Controller) en de controller voor de api (ApiController) niet gecombineerd kunnen worden. Ik heb zitten zoeken naar hoe ik dit zou moeten oplossen, maar ik denk dat het mij ontbreekt aan goede sleutelwoorden.

Mijn vraag is dus: Hoe zorg ik ervoor dat ik een reguliere MCV controller en een ApiController in één project kan verwerken en op de manier zoals in het voorbeeld beschreven kunnen werken? (Of zit ik nog ergens fout?)

Ik heb overigens geprobeerd in WebApiConfig.cs het pad voor de ApiController aan te passen naar "api/{controller}Api/{id}", maar dit lijkt niet te weken.

  • Grijze Vos
  • Registratie: December 2002
  • Laatst online: 28-02 22:17
Dit zou out of the box moeten werken.

Op zoek naar een nieuwe collega, .NET webdev, voornamelijk productontwikkeling. DM voor meer info


  • Erwin537
  • Registratie: December 2008
  • Laatst online: 18:25
Grijze Vos schreef op donderdag 21 maart 2013 @ 10:54:
Dit zou out of the box moeten werken.
Op welke manier? Ik kan de ApiController en de standaard Controller niet hetzelfde noemen.

Combineren kan (als ik het zo zie) ook niet, omdat de ene van het type ApiController is en de andere Controller. Ik kan het natuurlijk gewoon een Controller maken, maar dan werkt het Api pad niet meer?

  • InZane
  • Registratie: Oktober 2000
  • Laatst online: 23:39
Erwin537 schreef op donderdag 21 maart 2013 @ 10:50:
Beste,

Ik ben bezig met het maken van een prototype voor een webapplicatie framework/Visual Studio template waarbij het AJAX gebeuren al geregeld is. Hiervoor werk ik met REST, met een ApiController met daarin de CRUD acties. Het adres waar de requests naar toe worden gestuurd wil ik automatisch uit de URL halen.

Voorbeeld
Ik heb een test applicatie voor een boeken beheer. De overzicht pagina is te vinden op http://localhost:xxxx/Book/. Een javascript haalt /Book/ uit het adres en zorgt er voor dat AJAX (zoals create en delete) calls automatisch naar /api/Book/ gaan.



Nu heb ik echter het probleem dat de controller voor de gewone index pagina (Controller) en de controller voor de api (ApiController) niet gecombineerd kunnen worden. Ik heb zitten zoeken naar hoe ik dit zou moeten oplossen, maar ik denk dat het mij ontbreekt aan goede sleutelwoorden.

Mijn vraag is dus: Hoe zorg ik ervoor dat ik een reguliere MCV controller en een ApiController in één project kan verwerken en op de manier zoals in het voorbeeld beschreven kunnen werken? (Of zit ik nog ergens fout?)

Ik heb overigens geprobeerd in WebApiConfig.cs het pad voor de ApiController aan te passen naar "api/{controller}Api/{id}", maar dit lijkt niet te weken.
Edit: Lamaar, ik kan niet lezen.

[ Voor 4% gewijzigd door InZane op 21-03-2013 12:05 ]


  • Erwin537
  • Registratie: December 2008
  • Laatst online: 18:25
InZane schreef op donderdag 21 maart 2013 @ 12:02:
[...]


Dat laatste punt wat je noemt moet sowieso werken. Je moet alleen wel je RouteCondig daarop aanpassen natuurlijk.
Ik heb het aangepast in WebApiConfig, dan hoef ik in RouteConfig toch niets meer aan te passen?

Volgens mij had ik sowieso een denkfout, want ik wil juist bereiken dat een API controller en een MVC controller dezelfde naam hebben, maar dat ik de ene kan benaderen via http://localhost/api/{controller} en de ander via http://localhost/{controller}. Respectievelijk moet de één dus JSON terug geven en de ander een View.

EDIT:
Waar volgens mij dus het probleem zit is dat als ik er een Controller van maak, het "/api/Book/" pad niet werkt. Als ik er een ApiController van maak kan ik geen Views terug geven.

[ Voor 12% gewijzigd door Erwin537 op 21-03-2013 12:31 . Reden: typo ]


  • Megamind
  • Registratie: Augustus 2002
  • Laatst online: 10-09 22:45
Je zegt dat het niet werkt, maar wat werkt er precies niet? Als je routes goed staan zou het gewoon moeten werken. Krijg je een 404? Krijg je een exception?

  • Erwin537
  • Registratie: December 2008
  • Laatst online: 18:25
Megamind schreef op donderdag 21 maart 2013 @ 13:20:
Je zegt dat het niet werkt, maar wat werkt er precies niet? Als je routes goed staan zou het gewoon moeten werken. Krijg je een 404? Krijg je een exception?
Sorry, dat was ik even vergeten goed erbij te vermelden. Dit zie ik terug in de console:
{"Message":"No HTTP resource was found that matches the request URI 'http://localhost:55619/api/Book/'.","MessageDetail":"No type was found that matches the controller named 'Book'."}
Bovenstaande krijg ik dus terug op "http://localhost:55619/Book", terwijl ik gewoon de juiste index pagina terug krijg op: "http://localhost:55619/Book"

EDIT:
Net op iets andere trefwoorden het volgende topic gevonden:
http://stackoverflow.com/...controller-for-the-same-t
Ik moet er nog even goed naar kijken, maar ik geloof niet dat er echt een goede oplossing staat.

[ Voor 16% gewijzigd door Erwin537 op 21-03-2013 14:19 ]


  • Megamind
  • Registratie: Augustus 2002
  • Laatst online: 10-09 22:45
Je weet dat de "normale" routes en de webapi routes apart van elkaar zijn. Als je MVC4 gebruikt staan de routes in App_start onder "WebApiConfig.cs".

C#:
1
2
3
4
5
6
7
public static class WebApiConfig
{
    public static void Register(HttpConfiguration config)
    {
        config.Routes.MapHttpRoute("DefaultApi", "api/{controller}/{id}", new { id = RouteParameter.Optional });
    }
}

Deze worden dan weer vanuit je Global.asax aangeroepen:
C#:
1
WebApiConfig.Register(GlobalConfiguration.Configuration);


Als je zeker weet dat je routes goed staan dan moet er iets fout zitten in je webapi controller. Je moet dus een controller hebben die afgeleid is van de `ApiController`.

Maar je kan niet 2 maal een BookController hebben dus zal je die anders moeten noemen, en dan zal je ook je routes moeten aanpassen:

C#:
1
2
3
4
5
6
7
8
9
public static class WebApiConfig
{
    public static void Register(HttpConfiguration config)
    {
        config.Routes.MapHttpRoute("BookApi", "api/Book", new { Controller = "BookApi", "Action" = "Index" });

        config.Routes.MapHttpRoute("DefaultApi", "api/{controller}/{id}", new { id = RouteParameter.Optional });
    }
}

  • Erwin537
  • Registratie: December 2008
  • Laatst online: 18:25
Megamind schreef op donderdag 21 maart 2013 @ 14:21:
Je weet dat de "normale" routes en de webapi routes apart van elkaar zijn. Als je MVC4 gebruikt staan de routes in App_start onder "WebApiConfig.cs".
C#:
1
2
3
4
5
6
7
public static class WebApiConfig
{
    public static void Register(HttpConfiguration config)
    {
        config.Routes.MapHttpRoute("DefaultApi", "api/{controller}/{id}", new { id = RouteParameter.Optional });
    }
}
Dat weet ik inderdaad, vandaar eerder even mijn verwarring: als ik WebApiConfig aangepast heb, dan hoef ik RouteConfig toch niet aan te passen.
Deze worden dan weer vanuit je Global.asax aangeroepen:
C#:
1
WebApiConfig.Register(GlobalConfiguration.Configuration);
Dankje, dit geeft meer inzicht in hoe alles nou 'magisch' gebeurt.
Als je zeker weet dat je routes goed staan dan moet er iets fout zitten in je webapi controller. Je moet dus een controller hebben die afgeleid is van de `ApiController`.

Maar je kan niet 2 maal een BookController hebben dus zal je die anders moeten noemen, en dan zal je ook je routes moeten aanpassen:

C#:
1
2
3
4
5
6
7
8
9
public static class WebApiConfig
{
    public static void Register(HttpConfiguration config)
    {
        config.Routes.MapHttpRoute("BookApi", "api/Book", new { Controller = "BookApi", "Action" = "Index" });

        config.Routes.MapHttpRoute("DefaultApi", "api/{controller}/{id}", new { id = RouteParameter.Optional });
    }
}
Dat houdt in dat de routes handmatig geprogrammeerd moeten worden als ik het goed begrijp? Dat is niet helemaal de bedoeling.

Opgelost
Ik heb het nu opgelost met behulp van het topic in de vorige post, hier stond toch een goede oplossing.

Wat ik heb gedaan is een folder aangemaakt in de controllers folder. Daar heb ik mijn BookController gezet die is afgeleid van de ApiController. Omdat de twee BookControllers nu in een andere namespace staan kunnen ze beide hetzelfde heten.
Zonder verder nog iets aan de paden aan te passen blijkt dit te werken.

Ik heb nu wel het probleem dat als ik een boek aan wil maken de ModelState niet meer valid is, terwijl de gegevens correct zijn ingevuld. Voor zover ik weet is er verder niets veranderd. Als ik dit nog oplos laat ik nog weten of het relevant was.

EDIT:
Laatste test had ik schijnbaar niet zo opgelet.

Bedankt voor uw hulp :)

[ Voor 7% gewijzigd door Erwin537 op 21-03-2013 16:09 ]

Pagina: 1