0

I want use fullcalendar in my MVC project. My project include EWS API Exchange. I want get appointment in exchange. Also I am using ad authentication: Configure ASP.NET MVC for authentication against AD

I created a user model:

 public class AccountModels
    {
        [Required]
        [Display(Name = "User name")]
        public string UserName { get; set; }

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

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

Then AccountController:

     public ActionResult Login()
    {
        return View();
    }


    [HttpPost]
    [ValidateAntiForgeryToken]
    public ActionResult Login(AccountModels model, string returnURL)
    {
        if (!this.ModelState.IsValid)
        {
            return this.View(model);
        }
        if (Membership.ValidateUser(model.UserName, model.Password))
        {
            FormsAuthentication.SetAuthCookie(model.UserName, model.RememberMe);
            if (this.Url.IsLocalUrl(returnURL) && returnURL.Length > 1 && returnURL.StartsWith("/")
                && !returnURL.StartsWith("//") && !returnURL.StartsWith("/\\"))
            {
                return this.Redirect(returnURL);
            }
            return this.RedirectToAction("Index", "Home", model);
        }

        this.ModelState.AddModelError(string.Empty, "The username or password is incorrect");

        return this.View(model);
    }

    public ActionResult LogOff()
    {
        FormsAuthentication.SignOut();
        return this.RedirectToAction("Account", "Login");
    }

}

The model creation is fine and then I redirect to Home Controller on Index method. In Index method, I create my ExchnageServer, but after Index is done, my model object becomes null.

This Home Controller

    public ActionResult Index(AccountModels model)
    {
        ServerExchangeCore server = new ServerExchangeCore(model);
        return View(server);

    }

   // [Authorize]
    public JsonResult GetAppointments(ServerExchangeCore serverExchange)
    {
        ServerExchangeCore server = serverExchange;
        server.SetServer();
        JsonResult result = new JsonResult();
        List<Appointment> dataList = server.GetAppointments();
        result = Json(dataList, JsonRequestBehavior.AllowGet);
        return result;
    }

And this my ServerExchnageCore class

public class ServerExchangeCore
{
    ExchangeService service = new ExchangeService(ExchangeVersion.Exchange2016);
    AccountModels _model = new AccountModels();
    public ServerExchangeCore()
    { }
    public ServerExchangeCore(AccountModels model)
    {
        _model = model;
    }

    public void SetServer()
    {
        string email = GetEmail()
        service.Credentials = new WebCredentials(_model.UserName, _model.Password);
        service.AutodiscoverUrl(email, RedirectionUrlValidationCallback);

    }


    public List<Appointment> GetAppointments()
    {
        DateTime startDate = DateTime.Now;
        string sssssss = service.Url.ToString();
        DateTime endDate = startDate.AddDays(30);
        CalendarFolder calendar = CalendarFolder.Bind(service, WellKnownFolderName.Calendar, new PropertySet());
        CalendarView calendarView = new CalendarView(startDate, endDate);
        calendarView.PropertySet = new PropertySet(AppointmentSchema.Subject, AppointmentSchema.Start, AppointmentSchema.End);
        FindItemsResults<Appointment> appointments = calendar.FindAppointments(calendarView);
        List<Appointment> lst = new List<Appointment>();
        foreach (Appointment aa in appointments)
        {
            lst.Add(aa);
        }
        return lst;
    }

    private string GetEmail()
    {

        if (HttpContext.Current.User.Identity.Name != null && HttpContext.Current.User.Identity.IsAuthenticated)
        {

            MembershipUser user = Membership.GetUser();
            if (user != null)
                userEmail = user.Email;
        }
        userEmail = Membership.GetUser().Email;
        return userEmail;
    }

How do I fix my HomeController?

Rahul Sharma
  • 7,768
  • 2
  • 28
  • 54
Alex
  • 53
  • 12
  • _"my object become null"_ - which object? – vasily.sib Apr 05 '19 at 10:49
  • ServerExchangeCore server = new ServerExchangeCore(model); When i use `public void SetServer() { string email = GetEmail() service.Credentials = new WebCredentials(_model.UserName, _model.Password); service.AutodiscoverUrl(email, RedirectionUrlValidationCallback); } _model.UserName, _model.Password = null` – Alex Apr 05 '19 at 10:55
  • @Alex Are you able to get your model in your Home Controller in Index? Basically are you able to see the model here: `public ActionResult Index(AccountModels model)`? – Rahul Sharma Apr 05 '19 at 11:26
  • Yes, but after return View(server), launch execute script in Index.cshtml where call "/home/GetAppointments" And in this controller AccountModel become null – Alex Apr 05 '19 at 11:39
  • @Alex, as I can see you get to the Index action only through the Login action. So you need to log in every time to keep your model object not null. – NoImagination Apr 05 '19 at 11:41
  • And how save usermodel? Like other sites. – Alex Apr 05 '19 at 11:58
  • @Alex Basically when the login is successful, you then redirect the user to the `Index` page which is in your `Home` Controller. You could put your `AccountModels` properties as a session variable explicitly and then you can use these session variables throughout the life cycle of the program as long as the `LogOff` method is invoked which would destroy your Session and hence your objects. Something like this would work in your case: `Session["UserName"] = model.UserName; Session["Password"] = model.Password;` – Rahul Sharma Apr 05 '19 at 12:07
  • @Alex And remember if you use this, then storing password in session is not a good practice, therefore after your work is done by that value, you can set it to `null`. `//Use session variable //Set it to null once done Session["Password"] = null;` or `Session.Remove("Password");` – Rahul Sharma Apr 05 '19 at 12:14
  • Let me ask it another way, i can create object my class, which can be accessed by any controller and who is alive while user didn't close webpage? – Alex Apr 05 '19 at 13:47
  • @Alex You can use `HttpContext.Current.Application`:https://stackoverflow.com/questions/2266533/does-asp-net-mvc-have-application-variables but that will also cause problems as discussed here: https://stackoverflow.com/questions/25358448/why-my-httpcontext-application-variable-cannot-be-access-through-different-actio – Rahul Sharma Apr 05 '19 at 14:33
  • Thank you! And one question) If using "Session" in browser string i see username and password, can i hide it? – Alex Apr 05 '19 at 15:10
  • @Alex You can use a input of type `hidden` in your View to hide your variables. In razor: `@Html.HiddenFor("password" , new {id = "passwordID", value = "Your Password Session Value" })` – Rahul Sharma Apr 05 '19 at 15:53
  • @Alex Did you get this resolved? – Rahul Sharma Apr 06 '19 at 17:32
  • Sorry, but i can't figure out. In View where i create model `@Html.HiddenFor(model => model.UserName, new { id = "userNameID", value = "UserName"})` ` @Html.HiddenFor(model => model.Password, new { id = "passwordID", value = "UserName"})` then HomeController `public ActionResult Index(AccountModels model) { Session["UserName"] = model; return View(); }` But still i see password in browser string address( – Alex Apr 08 '19 at 11:46

2 Answers2

0

I found better solution https://blogs.msdn.microsoft.com/emeamsgdev/2012/11/05/ews-from-a-web-application-using-windows-authentication-and-impersonation/ Will try use it. Remains to understand how to get email address.

Alex
  • 53
  • 12
0

I resolve it with Kerberos, as link https://blogs.msdn.microsoft.com/emeamsgdev/2012/11/05/ews-from-a-web-application-using-windows-authentication-and-impersonation/

//create useracount

        IIdentity id = HttpContext.Current.User.Identity;
        id = Thread.CurrentPrincipal.Identity;
        id = WindowsIdentity.GetCurrent();
        string email = GetEmail(id);
        service.Credentials = new WebCredentials(CredentialCache.DefaultCredentials);

Then try get user's email address

      private string GetEmail(IIdentity id)
    {
        System.DirectoryServices.ActiveDirectory.Domain domain = System.DirectoryServices.ActiveDirectory.Domain.GetCurrentDomain();
        string address = String.Empty;
        using (HostingEnvironment.Impersonate())
        {
            using (var context = new PrincipalContext(ContextType.Domain, domain.Name, null, ContextOptions.Negotiate | ContextOptions.SecureSocketLayer))
            using (var userPrincipal = UserPrincipal.FindByIdentity(context, IdentityType.SamAccountName, id.Name))
            {
                address = userPrincipal.EmailAddress;
            }
        }
        return address;
    }
Alex
  • 53
  • 12