HowTo: ASP.NET MVC Projekt erstellen (erster Einstieg)

Im letzten MVC HowTo ging es um die Beweggründe für ASP.NET MVC – heute werfen wir einen ersten Blick auf das MVC Framework. Das ganze werde ich direkt praktisch in meinem “ReadYou” Projekt verwenden (das derzeit aufgrund von Zeitmangel etwas schleift).

Die Projektvorlage:

Wenn man sich die aktuelle ASP.NET MVC Version runtergeladen hat (momentan sind wir bei Preview 5 auf Codeplex) und ein neues Projekt anlegt, sieht man folgendes neue Item:

image

Anmerkung: Wenn man das deutsche Visual Studio benutzt, scheint die Projektvorlage nicht mit aufzutauchen, dazu muss man die Project- und Itemtemplates von 1033 in 1031 (z. B. C:\Program Files (x86)\Microsoft Visual Studio 9.0\Common7\IDE\ProjectTemplates\CSharp\Web\1031 bzw. \1033) kopieren und danach per Kommandozeile “devenv /installvstemplates” aufrufen. – Danke an “GarlandGreene” für den Hinweis.

Nachdem man dies ausgewählt hat kommt dieses Fenster:

image

Es wird angeboten sofort ein Unittest Projekt anzulegen. “Visual Studio Unit Test” (MS Test) ist per Default ausgewählt – später sollen allerdings noch weitere Test Frameworks (NUnit etc.) folgen.

Projektstruktur:

Nachdem die beiden Wizards durchgelaufen sind finden wir ungefähr (ich hab das UnitTest Projekt verschoben und umbenannt) so aus:

image

Aus der Ordnerstruktur ist auch bereits das MVC zu erkennen:

  • Kurzüberblick:
    • Controller: Logik
    • Models: Die eigentlichen Businessdaten
    • Views: Wie werden die Daten angezeigt

Views, Controller & Model:

Im ausgelieferten Stand besitzt das Template 2 Controller, 3 View-Ordner und ein Model-Ordner:

image

  • Im “Shared” Ordner werden alle Viewelemente gehalten, die für jeden View nützlich sind, wie z.B. die Masterpage oder eine Errorseite falls etwas schief läuft.
  • Jeder Controller besitzt seinen eigenen Ordner (“AccountController” – “Account” / “HomeController” – “Home“)
  • Diese “Pfade” können allerdings über Interfaces angepasst werden – ein Beispiel findet man z.B. hier “Partitioning an ASP.NET MVC application into separate “Areas”” oder Rob Conery Version.
  • Im Models Ordner können normale Klassen gespeichert werden – allerdings kann man diesen Ordner auch leer lassen, wenn man für die normalen Klassen bereits eine Klassenbibliothek hat.

Ein Blick auf die Seite:

Um einen ersten Blick auf die Funktionsweise des MVC Frameworks zu erhaschen ist die Startanwendung (welche bereits mit dem Membershipsystem, Masterpages etc.) ausgeliefert wird, ein guter Anfangspunkt:

image

image

Der Request Flow:

Justin Etheredge hat auf seinem Blog gut dargestellt, wie der Request einer MVC Anwendung verarbeitet wird und wo es überall die Möglichkeit gibt, selber einzugreifen: ASP.NET MVC Request Flow

Kommunikation zwischen Controller und View: Vom Controller zum View

image

 

Der Controller wird durch den Request Flow (siehe oben) aufgerufen – ich werde später noch eigene Controller in einem seperaten HowTo erstellen. Dabei kann man das ViewData Dictionary nutzen:

public ActionResult Index()
        {
            ViewData["Title"] = "Home Page";
            ViewData["Message"] = "Welcome to ASP.NET MVC!";

            return View();
        }

Durch den Aufruf der “View()“-Methode wird der View namens “Index” (weil die ControllerAction “Index” heisst) im “Home” Ordner aufgerufen (weil der Controller “Home” heisst).

Im View “Index.aspx” ist folgender Quellcode:

<%@ Page Language="C#" MasterPageFile="~/Views/Shared/Site.Master" AutoEventWireup="true" CodeBehind="Index.aspx.cs" Inherits="ReadYou.WebApp.Views.Home.Index" %>

<asp:Content ID="indexContent" ContentPlaceHolderID="MainContent" runat="server">
    <h2><%= Html.Encode(ViewData["Message"]) %></h2>
    <p>
        To learn more about ASP.NET MVC visit <a href="http://asp.net/mvc" title="ASP.NET MVC Website">http://asp.net/mvc</a>.
    </p>
</asp:Content>

Durch das einbinden der Masterpage (“MasterPageFile”) wird natürlich auch die Masterpage aufgerufen:

...
<head runat="server">
    <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />
    <title><%= Html.Encode(ViewData["Title"]) %></title>
</head>
...

Die Daten in dem “ViewData” werden sowohl in der Masterpage als auch in dem eigentlichen View angezeigt – ähnlich wie bei klassischem ASP.

Stark Typisierte Variante

Da das Dictionary nicht besonderes typisiert ist, kann man natürlich die ViewData auch noch streng typisiert hinterlegen. Dafür muss man in der Codebehinde Datei der ViewPage, welche im Ausgangszustand so aussieht:

namespace ReadYou.WebApp.Views.Home
{
    public partial class Index : ViewPage
    {
    }
}

Einen eigenen ViewData Typ hinterlegen:

Index.aspx.cs:

namespace ReadYou.WebApp.Views.Home
{
    public class IndexViewData
    {
        public string Text { get; set; }
    }

    public partial class Index : ViewPage<IndexViewData>
    {
    }
}

Index.aspx:

<%@ Page Language="C#" MasterPageFile="~/Views/Shared/Site.Master" AutoEventWireup="true" CodeBehind="Index.aspx.cs" Inherits="ReadYou.WebApp.Views.Home.Index" %>

<asp:Content ID="indexContent" ContentPlaceHolderID="MainContent" runat="server">
    <h2><%= Html.Encode(ViewData.Model.Text) %></h2>
    <p>
        To learn more about ASP.NET MVC visit <a href="http://asp.net/mvc" title="ASP.NET MVC Website">http://asp.net/mvc</a>.
    </p>
</asp:Content>

HomeController.cs:

        public ActionResult Index()
        {
            ViewData["Title"] = "Home Page";
            IndexViewData data = new IndexViewData();
            data.Text = "Hallo streng typisierter Text";
            ViewData.Model = data;
            return View();
        }

Hinweis: Das ViewData["Title"] wird nach wie vor von der Masterpage ausgewertet. In einer MVC Anwendung müssen alle Daten vom Controller übergeben werden – es existiert momentan (Preview 5) nur eine experimentelle Funktion, welche es erlaubt, dass der View sich Daten aus anderen Quellen holt – allerdings entspricht dies nicht der MVC Norm!

Mehr Informationen findet man in dem Blogpost von Scott Guthrie (damals Preview 3 – Konzept ist gleich geblieben, manche Sachen sind allerdings geändert wurden):
ASP.NET MVC Framework (Part 3): Passing ViewData from Controllers to Views

 

Kommunikation zwischen Controller und View: Vom View zum Controller

image 

Der View kann über normale Links oder HTML Formulare die Daten an einen Controller schicken. Ein Beispiel ist bereits in dem Template eingebaut: Der Login-Mechanismus – dafür schauen wir uns die Login.aspx an:

Variante 1: Per GET oder der “ActionLink”

Für alle die noch nicht angemeldet sind, gibt es auf der Loginseite einen kleinen Link zum Registrieren:

image

Im Code:

<p>
        Please enter your username and password below. If you don't have an account,
        please <%= Html.ActionLink("register", "Register") %>.
    </p>

Dieser Html Helper generiert den Link damit die Daten beim Klicken zum “AccountController” (der View befindet sich im “Account” Ordner) zur “Register” ActionMethode kommen.

Variante 2: Per POST

Der Username / Password wird in einem normalen Html Forumlar eingegeben:

    <form method="post" action="<%= Html.AttributeEncode(Url.Action("Login")) %>">
        <div>
            <table>
                <tr>
                    <td>Username:</td>
                    <td><%= Html.TextBox("username") %></td>
                </tr>
                <tr>
                    <td>Password:</td>
                    <td><%= Html.Password("password") %></td>
                </tr>
                <tr>
                    <td></td>
                    <td><input type="checkbox" name="rememberMe" value="true" /> Remember me?</td>
                </tr>
                <tr>
                    <td></td>
                    <td><input type="submit" value="Login" /></td>
                </tr>
            </table>
        </div>
    </form>

Die action-URL wird wieder über einen Html Helper generiert. Wenn der Nutzer das Formular abschickt, kommen die Daten in der “Login” ActionMethode des “AccountControllers” an:

        public ActionResult Login(string username, string password, bool? rememberMe)
        {

            ViewData["Title"] = "Login";

            // Non-POST requests should just display the Login form 
            if (Request.HttpMethod != "POST")
            {
                return View();
            }

            // Basic parameter validation
            List<string> errors = new List<string>();

            if (String.IsNullOrEmpty(username))
            {
                errors.Add("You must specify a username.");
            }
...
        }

Es gibt im MVC Framework einen eingebauten Mechanismus, der Formularwerte direkt auf Methoden-Parameter mappen kann (dies ist (natürlich) auch anpassbar). Dies ist nützlich, damit man die Methode besser mit UnitTests testen kann und kein Request Objekt sich erzeugen muss, sondern nur die Parameter entsprechend befüllen.

In der Methode werden Validierungen etc. vorgenommen. Man kann hier auch auf das normale Request Objekt zugreifen – allerdings sollte man um eine hohe Testbarkeit zu erreichen nicht direkt auf die Request Parameter zugreifen, sondern versuchen das Parametermapping zu verwenden. Stephen Walther hat dazu ein netten Blogpost darüber geschrieben.

Die Html Helper können auch “streng typisierte” sein und somit braucht man nicht unbedingt mit Strings Arbeiten (bei dem Actionlink z.B. direkt den Methodenaufruf über eine Expression anstatt “Register” als String zu schreiben) – Scott Hanselman hat einen Screencast dazu gemacht.

“Best Practices”, Tipps und Anlaufstellen

Da das MVC Framework noch nicht mal Beta ist, gibt es natürlich noch keine “Best Practices” – allerdings gibt es bereits mehrere interessante Projekte, welche mit MVC erstellt werden und Tipps geben:

Im nächsten HowTo werde ich dann genauer auf einzelne Teile eingehen – dies soll als Einstieg genügen.

Wenn dir der Blogpost gefallen hat, dann hinterlasse doch einen Kommentar. Wenn du auf dem Laufenden bleiben willst, abonniere unseren RSS Feed oder folge uns auf Twitter.

About the author

Written by

Hi, ich bin Robert Mühsig und bin Webentwickler und beschäftige mich mit Web-Frameworks auf dem Microsoft Web Stack und scheue mich auch nicht vor Javascript. Der Blog begann als "Problemsammelstelle und Lösungshilfe" und seitdem schreibe ich hier alles auf. Seit 2008 bin ich Microsoft MVP für ASP.NET. Treffen kann man mich online via Twitter (@robert0muehsig) oder hier.

6 Responses

  1. Hallo Robert

    Die Codecamp Applikation passt hier sicherlich auch noch gut rein. Das ist eine schöne Referenzapplikation für ASP.NET MVC:
    - http://code.google.com/p/codecampserver/

    Reply

Comment on this post

Letzte Posts

  • image_thumb.png
    NuGet Package Restore & Build Server wie z.B. AppVeyor

    NuGet ist ja mittlerweile weit verbreitet, aber eine Frage stellt sich natürlich immer noch: Checkt man die NuGet Packages ein oder nicht? In meinem kleinen Side-Projekt, welches auf GitHub liegt und ich über AppVeyor auch bauen lasse nutze ich das Package Restore Feature von NuGet, d.h. in meinem Repository befindet sich kein NuGet Package mehr, […]

  • image.png
    Microsoft Account Login via ASP.NET Identity

    Der Microsoft Account ist die zentrale Identifikationsstelle in der “Consumer-Microsoft-Welt”, allerdings ist das Einbinden eben dieser in die eigene Applikation eher schwierig. Das “Live SDK” ist nun unter dem OneDrive Dev Center zu finden und ganz professionell wurden auch alle Links zum alten Live SDK damit unbrauchbar gemacht. Beim Microsoft Account ist es auch unmöglich […]

  • image.png
    Zeitgesteuerte Azure WebJobs – so einfach kann Azure sein

    Das noch in Entwicklung befindliche Azure WebJob SDK bietet einige coole Features zum Verarbeiten und Bereitstellen von Daten. Bekanntes Beispiel ist das Sample welches auf eine Azure Queue lauscht und sobald ein Item da vorhanden ist anfängt dies zu verarbeiten. Szenario: Zeitgesteuerte Aktivitäten – ohne Queue und co. Mein Szenario war allerdings wesentlich trivialer: Ich […]

  • image.png
    Get Involved in OSS! Ja, aber wie geht das denn mit GitHub?

    Auch im .NET Lager gibt es Bewegung im OSS Bereich und es gibt verschiedene Arten wie man bei einem Open Source Projekt “Contributed”. Was zählt alles zu “Contribution”? Unter “Contribution” läuft eigentlich alles – ob es Fragen/Probleme zu dem Projekt via Issues ist oder Dokumentation nachreicht oder ob man darüber bloggt oder das Projekt vorstellt. […]

  • HowTo: Web.config samt eigener ConfigSection zur Laufzeit ändern

    In dem HowTo geht es darum wie man die Web.config zur Laufzeit ändert und was es dabei zu beachten gilt. Das ganze klappt auch mit komplexeren ConfigSections. Eigene ConfigSection? Vor einer ganzen Weile habe ich mal über das Erstellen einer eigenen ConfigSection geschrieben – im Grunde nutzen wir jetzt fast dieselbe Config. Zur Laufzeit? Startet […]

Amazon Shop

Facebook