How do I programatically create a user and NOT persist it?

Topics: Customizing Orchard
Oct 1, 2012 at 6:33 PM

How do I generate a user and NOT persist it? I have my own MemberShipService.cs file and for testing I am just creating a hard coded user(If I can get past this point I will try an external db)

Here is the code I have so far:

        public IUser ValidateUser(string userNameOrEmail, string password) {
            var lowerName = userNameOrEmail == null ? "" : userNameOrEmail.ToLowerInvariant();

            if (lowerName == "myadmin")
            {
                ContentItem i = _orchardServices.ContentManager.New("User");

                UserPart r = i.As<UserPart>();

                        r.Record.Email = "";
                        r.Record.EmailChallengeToken = "";
                        r.Record.EmailStatus = UserStatus.Approved;
                        r.Record.HashAlgorithm = "";
                        r.Record.Id = 10000;
                        r.Record.NormalizedUserName = lowerName;
                        r.Record.Password = "";
                        r.Record.PasswordFormat = MembershipPasswordFormat.Encrypted;
                        r.Record.PasswordSalt = "";
                        r.Record.RegistrationStatus = UserStatus.Approved;
                        r.Record.UserName = "MyAdmin";

                return i.As<UserPart>();
            }

Oct 1, 2012 at 8:31 PM

ug, I can't figure this out. I just want to create an IUser object and pass it back. but User.Id = 0 after the login. It say's 'welcome to orchard' but  'sign-in' still shows up.

Coordinator
Oct 1, 2012 at 8:48 PM

Did you try looking at existing test code for users?

Oct 1, 2012 at 11:41 PM
Edited Oct 1, 2012 at 11:46 PM

I looked at MembershipServiceTests.cs and all it did was to create a user with:

var user = _membershipService.CreateUser(new CreateUserParams("a", "b", "c", null, null, true

 So I tried that but commented out the commit line in the CreateUser method:  

I get the same result as my original attempt. that is user.id = 0 and that I am not logged in. No errors thrown.

//_orchardServices.ContentManager.Create(user);

));

Also contentItemRecord is null.

 

 

Coordinator
Oct 2, 2012 at 2:23 AM

How is user.id==0 an issue? Why do you think you should be logged in? What is it exactly that you are doing, and what do you expect to happen?

Oct 2, 2012 at 5:39 AM
Edited Oct 2, 2012 at 5:41 AM

I am going to have two User stores. One that is an external user store that already exists and the second being the default orchard users. During authentication I will check the external store first and then if the user does not exist in there I will check the orchard user store. The reason I want to do this is because our existing customers already have ActiveDirectory accounts that we access using LDAP API. Our customers don't want to create another username and password to use Orchard. They want to use what they already have. However, I still want the ability to add orchard users for new customers or anyone that doesn't have an AD.

I need the user.id to be filled because that is what links the roles to the users. I had planned on seeding the user.id from the external user store starting at 500,000 so as not to conflict with the orchard user store.

For a test, I copied the Orchard.Users.Services.MembershipServices.cs and modified it so the ValidateUser method returns my IUser object when the username equals 'myadmin'. What I had missed is that I had to also create a new version of Orchard.Security.Providers.FormsAuthenticationService.cs and modify the GetAuthenticatedUser method to also create my IUser object.

There has got to be some way to set user.id?

Here is the ValidateUser method in the MembershipService class:

        public IUser ValidateUser(string userNameOrEmail, string password) {
            var lowerName = userNameOrEmail == null ? "" : userNameOrEmail.ToLowerInvariant();

            if (lowerName == "myadmin")
            {
                UserPart r = new UserPart();

                r.Record = new UserPartRecord();

                r.Record.Email = "";
                r.Record.EmailChallengeToken = "";
                r.Record.EmailStatus = UserStatus.Approved;
                r.Record.HashAlgorithm = "";
                r.Record.NormalizedUserName = lowerName;
                r.Record.Password = "";
                r.Record.PasswordFormat = MembershipPasswordFormat.Encrypted;
                r.Record.PasswordSalt = "";
                r.Record.RegistrationStatus = UserStatus.Approved;
                r.Record.UserName = "MyAdmin";
                r.Record.Id = 10000;

                r.ContentItem = new ContentItem();

                return r;
            }

            var user = _orchardServices.ContentManager.Query<UserPart, UserPartRecord>().Where(u => u.NormalizedUserName == lowerName).List().FirstOrDefault();

            if (user == null)
                user = _orchardServices.ContentManager.Query<UserPart, UserPartRecord>().Where(u => u.Email == lowerName).List().FirstOrDefault();

            if ( user == null || ValidatePassword(user.As<UserPart>().Record, password) == false )
                return null;

            if ( user.EmailStatus != UserStatus.Approved )
                return null;

            if ( user.RegistrationStatus != UserStatus.Approved )
                return null;

            return user;
        }

and here is the GetAuthenticatedUser method for the FormsAuthenticationService:

        public IUser GetAuthenticatedUser() {
            if (_signedInUser != null)
                return _signedInUser;

            var httpContext = _httpContextAccessor.Current();
            if (httpContext == null || !httpContext.Request.IsAuthenticated || !(httpContext.User.Identity is FormsIdentity)) {
                return null;
            }

            var formsIdentity = (FormsIdentity)httpContext.User.Identity;
            var userData = formsIdentity.Ticket.UserData;
            int userId;
            if (!int.TryParse(userData, out userId)) {
                Logger.Fatal("User id not a parsable integer");
                return null;
            }
            if (userId == 0)
            {
                return getTest();
            }
            return _contentManager.Get(userId).As<IUser>();
        }

        private IUser getTest()
        {
            ContentItem i = _contentManager.New("User");


            UserPart r = i.As<UserPart>();

            r.Record.Email = "";
            r.Record.EmailChallengeToken = "";
            r.Record.EmailStatus = UserStatus.Approved;
            r.Record.HashAlgorithm = "";
            r.Record.NormalizedUserName = "myadmin";
            r.Record.Password = "";
            r.Record.PasswordFormat = MembershipPasswordFormat.Encrypted;
            r.Record.PasswordSalt = "";
            r.Record.RegistrationStatus = UserStatus.Approved;
            r.Record.UserName = "MyAdmin";
            r.Record.Id = 10000;

            return r;
        }

Coordinator
Oct 2, 2012 at 7:44 AM

So then you need to create *and persist* a real user.

Oct 3, 2012 at 4:10 AM
Edited Oct 3, 2012 at 4:15 AM

Hmm, I don't want to do that because then I would have duplication of data. I found out how to set the user.id field:

            ContentItem i = new ContentItem()
            {
                VersionRecord = new ContentItemVersionRecord()
                {
                    ContentItemRecord = new ContentItemRecord()
                    {
                        Id = 500002
                    }
                }
            };
            UserPart r = new UserPart()
            {
                Record = new UserPartRecord()
                {
                    Email = "",
                    EmailChallengeToken = "",
                    EmailStatus = UserStatus.Approved,
                    HashAlgorithm = "",
                    NormalizedUserName = username.ToLowerInvariant(),
                    Password = "",
                    PasswordFormat = MembershipPasswordFormat.Encrypted,
                    PasswordSalt = "",
                    RegistrationStatus = UserStatus.Approved,
                    UserName = username
                }
            };

            i.Weld(r);
            return r;