ASP.Net MVC 4 Simple Membership specify Schema - authentication

I'm trying to figure out how to setup ASP.Net MVC 4's Simple Membership. The tables that house users in my current database have a different schema then 'dbo'. How can I specify the schema when initializing my database connection:
WebSecurity.InitializeDatabaseConnection
(
connectionStringName: "GuessAListConnection",
userTableName: "UserProfile",
userIdColumn: "UserId",
userNameColumn: "UserName",
autoCreateTables: false
);
There's not an option for schema. I've tried appending schema to the userTableName but that produces an error. Any suggestions?
Thanks
Tom

WebSecurity will use whatever the default schema of the database user. No way to specify a different schema that i'm aware of.

I found another solution if you have your user/authentication tables in a different schema than dbo (or whatever the default schema of the database user) and that's to use a view.
In my database, my user/authentication tables are scoped to a "Security" schema. I also have a Person schema where the Person table lives. I store just FirstName, LastName in Person table.
I created a view that pulls all of the tables together for authentication and am returning the following fields:
UserId, UserName, PersonId, FirstName, LastName, AuthenticationType, LastLoginDate, IsLockedOut
In my application, I can authenticate a person a number of different ways: Form, Windows, Facebook, Twitter, etc. The UserId, UserName relate to the different authentication type.
Here's my UserProfile class in ASP.Net MVC:
[Table("__vwRegisteredUser")]
public class UserProfile
{
[Key]
[DatabaseGeneratedAttribute(DatabaseGeneratedOption.Identity)]
public int UserId { get; set; }
public String UserName { get; set; }
public int PersonId { get; set; }
public String FirstName { get; set; }
public String LastName { get; set; }
public String AuthenticationTypeName { get; set; }
public Boolean IsLockedOut { get; set; }
public DateTime LastLoginDate { get; set; }
public int Id
{
get
{
return PersonId;
}
}
public String Name
{
get
{
return String.Format("{0} {1}", FirstName, LastName);
}
}
}
Notice I use a view for the Table attribute. I'm also returning PersonId as an Id property and concatenating FirstName and LastName together as a Name property. The UserName is the value coming back from my Authentication Type (Windows user name, email address if I'm using Forms authentication, or whatever Facebook or Twitter returns). So, there's no consistency for UserName from my Security.Authentication table.
Initializing database connection still requires a table in order for SimpleMembership to generate membership tables. There maybe a way to have a custom membership table, but I haven't figured that out yet.

Related

ASP.Net Web API partial response base on a role

I know this is an old question, but could not find an answer for ASP.Net Core. I have ASP.Net Core web api application with role-based membership. Suppose we have an enitity from database with such fields:
public class Transaction
{
public int Id { get; set;}
public string UserId { get; set; }
public string ManagerId { get; set; }
public decimal Amount { get; set; }
}
And controller action:
[Authorize(Roles = "Admin,Manager,RegularUser")]
public async Task<IActionResult> Transactions(TransactionsRequest request)
{
var response = await _repository.Find(request, User);
return Ok(response);
}
My goal is to query and return partial result based on a role:
For Admin role I need to return all transations with all fields
For Manager role I need to return trasactions for current manager (based on managerId) without UserId field
For RegularUser role I need to return trasactions for current user (based on userId) without ManagerId field
I think it is simple to make three different actions, each one for specific role. But what if my role number will grow?

Entity Framework Core Code First Model Navidation Properties

I have a Web API that uses entity framework. I have several tables there were created using the code first setup. My Competitions class is defined below.
Everything works great and I'm able to get my Competitions table data along with all the data in the navigation properties that are returning a collection. However, I'm not able to get any values for the CompetitionTypes and Users navigation properties. OwnerId references UserId in the Users table.
How would I get the linked data in my CompetitionTypes and Users table? I basically want the same thing as the three collection navigation properties, except that CompetitionTypes and Users would only return one row.
public partial class Competitions
{
[Key, Required]
public int CompetitionId { get; set; }
public int CompetitionTypeId { get; set; }
public int OwnerId { get; set; }
public string CompetitionName { get; set; }
public CompetitionTypes CompetitionTypeId { get; set; }
public Users UserId { get; set; }
public ICollection<Participants> Participants { get; set; }
public ICollection<ResultStats> ResultStats { get; set; }
public ICollection<Results> Results { get; set; }
}
}
EF auto-matches FK properties with navigation properties based on conventions. Namely, it expects FK properties to be named the same as navigation properties, just with Id at the end. In other words, for it to automatically match up OwnerId, you'd need a navigation property like:
public User Owner { get; set; }
Since your navigation property is UserId, it's actually looking for a property named UserIdId.
If you don't want to follow conventions, then you must either use the ForeignKey attribute or fluent config to tell EF which property belongs with which.
That said, there's some pretty major issues with your naming of things here. First, entities should always be singular User, not Users. Second, you should not have navigation properties that end with Id: e.g., User, not UserId. Only actual PK or FK properties should end with with Id. Finally, don't prefix properties on your entity with the entity name. This last one is mostly for readability. Which is more natural: competition.Id or competition.CompetitionId? Likewise with CompetitionName; it should just be Name. And, for what it's worth, you don't need Required for either a primary key or a non-nullable type (such as int). In either case, the property is required by default.

Get current user logged in in Custom Authentication MVC 4

I have created a simple login table without simplemembership because in my project i don't need to have a register, the users need to be created automatically in the database. (Made following this tutorial).
I have a model Login:
public class Login
{
public virtual int UserId { get; set; }
public virtual string Username { get; set; }
public virtual string Password { get; set; }
public virtual List<Enrollment> Enrollments { get; set; }
}
and Enrollments:
public class Enrollment
{
public virtual int EnrollmentId { get; set; }
public virtual string Name { get; set; }
public virtual List<Login> Users { get; set; }
}
And i have a table Enrollment_Login because of the many-to-many relationship.
I need to create a view where i show a list of enrollments that the user logged in is "registered".
I have this query:
var query= from name in db.Enrollments
where name.Logins.Any(c=>c.LoginId==??)
select name;
If this query is right, how can i get the current user logged in?
You can't get the LoginId (which I think is a foreign key of your Login entity in Enrollement entity)
When user is authenticated the the name of that user is stored in this.User.Identity.Name if you're in your action method.
The name in your case is the UserName property in Login entity.
So you must write the following code :
var currentLogin = db.Logins.Single(u => u.UserName = this.User.Identity.Name);
var query= from name in db.Enrollments
where name.Logins.Any(c=>c.LoginId==currentLogin.Id)
select name;
Or in one query:
var query= from enrollement in db.Enrollments
join login in db.Logins on enrollement.LoginId equals login.UserId
where login.UserName == this.User.Identity.Name
select enrollement;

dapper populate DropDownlist

I have a simple Poco
public virtual short UserID
{
get;
set;
}
[Required]
public virtual string UserName
{
get;
set;
}
public virtual string Password
{
get;
set;
}
public virtual string Email
{
get;
set;
}
Im currently Using Dapper ORM.
Does anyone have a good example of how I would query using dapper ORM to create a drop-down-list?
The query should return Key=UserID and Value=UserName in a list so that I can retrieve the keys and populate the DropDownList.
you can create a class representing the pair:
class SelectItem
{
public long Key {get;set;}
public string Value {get;set;}
}
var list = connection.Query<SelectItem>(" select id Key UserName Value from yourtable",null).ToList();
you use the aliases to map the table fields to the class properties names. I'm supposing your table field names are id and UserName, change them according to your case.
You should also pay attention to the property types, you can have a bad cast exception if they don't match.
ALternatively, you can use the dynamic version:
var list = connection.Query(" select id Key UserName Value from yourtable",null).ToList();
you obtain a list of dynamics each with property named Key and UserName.

Entity Framework Code First - using UserId key of Memberships/Users table as Foreignkey in a custom table

I am trying to create a SQL table to include additional user information.
I want it to be created by Migrations in VS2012 (package console => update-database).
I see that there are two tables using UserId column as key: Memberships and Users tables.
I am trying to define the following class and map it to SQL table via Migrator:
[Key]
[Column(Order = 0)]
[ForeignKey("User")]
public Guid **UserId** { get; set; }
[Key]
[Column(Order = 1)]
[ForeignKey("Category")]
public int CategoryId { get; set; }
public virtual Category Category { get; set; }
**public virtual User User { get; set; }**
Although it is obvious in the Users SQL table that UserId column is the key, I get this error message:
\tSystem.Data.Entity.Edm.EdmEntityType: : EntityType 'User' has no key defined. Define the key for this EntityType.
\tSystem.Data.Entity.Edm.EdmEntitySet: EntityType: EntitySet 'Users' is based on type 'User' that has no keys defined.
What I am missing here? Might be that Microsoft.VisualBasic.ApplicationServices.User / System.Web.Security.MembershipUser classes weren't necessarily mapped to the tables this way and vise versa, and therefore the UserId property is not declared is Key dataannotation?
I am open for other solutions for this problem.
Big Thanks!
I am currently using asp.net mvc4 with Azure db.
When I want to use UserId in other tables from UserProfile. Notice in AccountModels there is class UserProfile:
[Table("UserProfile")]
public class UserProfile
{
[Key]
[DatabaseGeneratedAttribute(DatabaseGeneratedOption.Identity)]
public int UserId { get; set; }
public string UserName { get; set; }
}
Now, let's say your category is created by certain user, you can link category entry to user in following way.
[Table("Category")]
public class Category
{
[Key]
[DatabaseGeneratedAttribute(DatabaseGeneratedOption.Identity)]
public int CategoryId { get; set; }
public UserProfile CreatorUserId { get; set; }
}
Otherwise, you can always use UserProfile as model.