Copied to clipboard

Flag this post as spam?

This post will be reported to the moderators as potential spam to be looked at


  • Hefin Jones 38 posts 160 karma points
    Feb 20, 2014 @ 12:16
    Hefin Jones
    0

    Umbraco Helper - TypedContentAtXPath

    Umbraco Version: 7.0.3

    Hello all,

    I'm currently working on a MemberLoginSurfaceController with the following action for loggin out:

       // The MemberLogout Action signs out the user and redirects to the site homepage
            [HttpGet]
            public ActionResult MemberLogout()
            {
                Session.Clear();
                FormsAuthentication.SignOut();
                var umbracoHelper = new UmbracoHelper(UmbracoContext.Current);
                var homePage = umbracoHelper.TypedContentAtXPath(".//ancestor-or-self::Homepage[@level=2 and @isDoc]").FirstOrDefault();
                return RedirectToUmbracoPage(homePage);
            }

    As you can see I am trying to redirect to the homepage of the current site, I have a structure like this:

    Content (Root)
    --- Intro page (splash page)
    ------ Home (en)
    --------- Page 1 en
    --------- Page 2 en
    --------- etc ...
    ------ Home (cy)
    --------- Page 1 cy
    --------- Page 2 cy
    --------- etc ...

    What I'm trying to do is redirect the user to the relevant homepage when loggin out, depending on which site they are viewing.  I used to be able to do this using code similar to this:

    umbraco.uQuery.GetNodesByXPath("$currentPage/ancestor-or-self::Homepage[@level=2 and @isDoc]").FirstOrDefault().Id

    But the Umbraco Helper TypedContentAtXPath doesn't seem to like $currentPage.

    Is there a way I can replicate the uQuery method using TypedContentAtXPath?

  • Matt Linsenbardt 24 posts 147 karma points
    Feb 20, 2014 @ 19:42
    Matt Linsenbardt
    0

    Hi Hefin,

    You have a couple of options using the IpublishedContent model:

    Traverse by contentTypeAlias
    Model.Content.Ancestor('Home").Url

    Traverse by level
    Model.Content.Ancestor(2).Url

    I see that you are using a surface controller. Were you able to get the ModelState errors to bubble back up to your View (e.g. login errors)?

    - Matt 

  • Hefin Jones 38 posts 160 karma points
    Feb 20, 2014 @ 21:29
    Hefin Jones
    0

    Hi Matt,

    I don't seem to have the option of using Model.Content.Ancestor("Home").Url or Model.Content.Ancestor(2).Url - I imagine that this is because I'm using a custom model?  

    public class MemberLoginModel
    {
    [Required, Display(Name = "Enter your username")]
    public string Username { get; set; }

    [Required, Display(Name = "Password"), DataType(DataType.Password)]
    public string Password { get; set; }

    [Display(Name = "Remember me")]
    public bool RememberMe { get; set; }

    In answer to your question, yes I do get the ModelState errors bubble back to my view, I call the partial view of "_MemberLogin" like this:

    @Html.Partial("_MemberLogin", new dpp.models.Shared.MemberLoginModel())

    Would this also me contributing to my issue in getting hold of the current page in the controller?  

    - Hefin

  • Matt Linsenbardt 24 posts 147 karma points
    Feb 20, 2014 @ 22:06
    Matt Linsenbardt
    0

    You can inherit from the RenderModel to gain access to the Content class.

    publicclassMemberLoginModel : Umbraco.Web.Models.RenderModel
    {
    [Required,Display(Name="Enter your username")]
    publicstringUsername{get;set;}
     
    [Required,Display(Name="Password"),DataType(DataType.Password)]
    publicstringPassword{get;set;}
     
    [Display(Name="Remember me")]
    publicboolRememberMe{get;set;}

    public MemberLoginModel() : this(UmbracoContext.Current.PublishedContentRequest.PublishedContent) {}
    public MemberLoginModel(IPublishedContent content) : base(content) {}

    }

  • Hefin Jones 38 posts 160 karma points
    Feb 21, 2014 @ 14:58
    Hefin Jones
    0

    Hi Matt - still don't get the Model.Content.Ancestor("Home").Url or Model.Content.Ancestor(2).Url.  I'm doing this in the Surface Controller .... here is my code for the Surface Controller:

    public class MemberLoginSurfaceController : SurfaceController
    {
    // The MemberLogin Action returns the view. it also instantiates a new, empty model for our view
    [HttpGet]
    [ActionName("MemberLogin")]
    public ActionResult MemberLoginGet()
    {
    return PartialView("_MemberLogin", new MemberLoginModel());
    }

    // The MemberLogout Action signs out the user and redirects to the site homepage
    [HttpGet]
    public ActionResult MemberLogout()
    {
    Session.Clear();
    FormsAuthentication.SignOut();
    return Redirect("/");
    }

    // The MemberLoginPost checks the entered credentials using the standard ASP.NET membership provider and redirects the user to the same page
    [HttpPost]
    [ActionName("MemberLogin")]
    public ActionResult MemberLoginPost(MemberLoginModel model)
    {
    if (ModelState.IsValid)
    {
    if (Membership.ValidateUser(model.Username, model.Password))
    {
    FormsAuthentication.SetAuthCookie(model.Username, model.RememberMe);
    return RedirectToUmbracoPage(Settings.LocalSettingsNode.GetPropertyValue("membersHomepage"));
    }
    else
    {
    ModelState.AddModelError("", "Login data is incorrect!");
    }
    }
    return CurrentUmbracoPage();
    }
    }

    And it's the MemberLogout() action where I'm trying to do the redirect.  So instead of having 

    return Redirect("/");

    I would like to do something like:

    return RedirectToUmbracoPage()

    But I can't seem to get it to work?

  • Matt Linsenbardt 24 posts 147 karma points
    Feb 21, 2014 @ 17:07
    Matt Linsenbardt
    0

    Hi Hefin,

    It appears to be very difficult to get the Umbraco Context from your GET as your not on a page. Perhaps it would be easier to pivot slightly and pass a url parameter to your get and redirect to that url after SignOut.

  • Hefin Jones 38 posts 160 karma points
    Mar 05, 2014 @ 17:45
    Hefin Jones
    100

    Hi Matt,

    I implemented something along those lines.  In my partial view I now have this:

    <p>@Html.ActionLink("Log out", "MemberLogout", "MemberLoginSurface", new { homePageId = dpp.library.Extensions.Settings.PageIDs.HomepageID }, null)</p>

    Which uses gets the home page of the current node from a class which returns the homepage Id:

    public static int HomepageID
    {
    get
    {
    int id = 0;
    id = umbraco.uQuery
    .GetNodesByXPath("$currentPage/ancestor-or-self::Homepage[@level=2 and @isDoc]").FirstOrDefault().Id;
    return id;
    }
    }

    Now my controller action looks like this:

    [HttpGet]
    public ActionResult MemberLogout(int homePageId)
    {
    Session.Clear();
    FormsAuthentication.SignOut();
    return RedirectToUmbracoPage(homePageId);
    }

    Might not be the perfectly correct solution but it works for me.

  • This forum is in read-only mode while we transition to the new forum.

    You can continue this topic on the new forum by tapping the "Continue discussion" link below.

Please Sign in or register to post replies