UNIT TEST URL.islocalUrl (returnUrl.ToString ()), comment puis-je le faire retourner false dans le test unitaire?

StackOverflow https://stackoverflow.com/questions/9463201

Question

À partir de la méthode de connexion standard dans le contrôleur de compte dans les applications MVC3, comment puis-je tester le

Url.IsLocalUrl(returnUrl.ToString()) 

ligne de code où l'URL n'est pas locale? En d'autres termes, quelle URL dois-je alimenter cette ligne de code lors des tests unitaires, pour le faire revenir faux?

J'ai utilisé la pensée suivante que cela serait retourné comme faux (non local):

Uri uri = new Uri(@"http://www.google.com/blahblah.html");

Mais il a juste lancé une exception nul dans les tests unitaires

Edit: je dois ajouter que la méthode de connexion ressemble maintenant à ceci:

public ActionResult LogOn(LogOnModel model, System.Uri returnUrl)

if (ModelState.IsValid) {

            bool loggedOn = LogOn(model);

            if (loggedOn) {
                if (Url.IsLocalUrl(returnUrl.ToString())) {
                    return Redirect(returnUrl.ToString());
                }
                else {
                    return RedirectToAction("Index", "Home");
                }
            }
            else {
                ModelState.AddModelError("", "The user name or password provided is incorrect.");
            }
        }

        // If we got this far, something failed, redisplay form
        return View(viewModel);
    }

Certaines erreurs d'analyse COP / Code de style ont forcé une modification d'un paramètre de chaîne à System.uri, mais il est très similaire à l'original standard.

Juste pour clarifier, dans un test unitaire - je veux tester et affirmer l'issue de la frappe Else ligne où il redirige vers Home/Index, j'ai donc besoin de passer quelque chose dans le (System.Uri)returnUrl Cela le fera revenir faux Url.IsLocalUrl Et ne pas lancer une exception

Modifier plus loin:

J'utilise MVCContrib Testhelper, ce qui est assez bon pour se moquer de beaucoup de trucs HTTPContext et Web:

Builder = new TestControllerBuilder();
UserController = new UserController();
    Builder.InitializeController(UserController);
Était-ce utile?

La solution

Vous devez vous moquer du HTTPContext ainsi que de l'instance URLHELPER sur le contrôleur que vous êtes unité de test. Voici un exemple de la façon dont ce test unitaire pourrait ressembler si vous utilisez MOQ:

[TestMethod]
public void LogOn_Should_Redirect_To_Home_If_Authentication_Succeeds_But_Not_Local_ReturnUrl_Is_Provided()
{
    // arrange
    var sut = new AccountController();
    var model = new LogOnModel();
    var returnUrl = new Uri("http://www.google.com");
    var httpContext = new Mock<HttpContextBase>();
    var request = new Mock<HttpRequestBase>();
    httpContext.Setup(x => x.Request).Returns(request.Object);
    request.Setup(x => x.Url).Returns(new Uri("http://localhost:123"));
    var requestContext = new RequestContext(httpContext.Object, new RouteData());
    sut.Url = new UrlHelper(requestContext);

    // act
    var actual = sut.LogOn(model, returnUrl);

    // assert
    Assert.IsInstanceOfType(actual, typeof(RedirectToRouteResult));
    var result = (RedirectToRouteResult)actual;
    Assert.AreEqual("Home", result.RouteValues["controller"]);
    Assert.AreEqual("Index", result.RouteValues["action"]);
}

Remarque: Puisque vous avez réellement montré le LogOn implémentation que vous appelez pour vérifier les informations d'identification, vous devrez peut-être adapter le test unitaire pour vous assurer que cette méthode renvoie vraie en premier lieu compte tenu du modèle afin d'entrer dans le if (loggedOn) clause.


METTRE À JOUR:

Il semble que vous utilisez Mvccontrib.testhelper qui fait toute la configuration de moquerie HttpContext pour vous. Donc, tout ce que vous devez faire est de se moquer des pièces pertinentes pour votre test unitaire:

[TestMethod]
public void LogOn_Should_Redirect_To_Home_If_Authentication_Succeeds_But_Not_Local_ReturnUrl_Is_Provided()
{
    // arrange
    var sut = new AccountController();
    new TestControllerBuilder().InitializeController(sut);
    var model = new LogOnModel();
    var returnUrl = new Uri("http://www.google.com");
    sut.HttpContext.Request.Expect(x => x.Url).Return(new Uri("http://localhost:123"));

    // act
    var actual = sut.LogOn(model, returnUrl);

    // assert
    actual
        .AssertActionRedirect()
        .ToController("Home")
        .ToAction("Index");
}

Normalement, les 2 premières lignes du test unitaire pourraient être déplacées vers le monde [SetUp] Méthode pour éviter de les répéter dans chaque test unitaire pour ce contrôleur afin que maintenant votre test devienne un peu plus propre:

[TestMethod]
public void LogOn_Should_Redirect_To_Home_If_Authentication_Succeeds_But_Not_Local_ReturnUrl_Is_Provided()
{
    // arrange
    var model = new LogOnModel();
    var returnUrl = new Uri("http://www.google.com");
    _sut.HttpContext.Request.Expect(x => x.Url).Return(new Uri("http://localhost:123"));

    // act
    var actual = _sut.LogOn(model, returnUrl);

    // assert
    actual
        .AssertActionRedirect()
        .ToController("Home")
        .ToAction("Index");
}
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top