Get all Identity roles in ASP .Net Core WebAPI - asp.net-web-api

I have a task to fetch all identity roles in my database. i use below code to fetch all roles. in Asp .Net core WebAPI
UserRoleService.cs
public class UserRoleService
{
private readonly RoleManager<IdentityRole> _roleManager;
public UserRoleService(RoleManager<IdentityRole> roleManager)
{
_roleManager=roleManager;
}
public Task<IList<string>> AllUserRoles(){
return _roleManager.Roles;
}
}
But i got following Error
Cannot implicitly convert type
'System.Linq.IQueryable<Microsoft.AspNetCore.Identity.IdentityRole>' to
'System.Threading.Tasks.Task<System.Collections.Generic.List<string>>'.
An explicit conversion exists (are you missing a cast?)
plese give me a solution to solve this error
when i change it to
Task<List<IdentityRole>> AllUserRoles()
{
return _roleManager.Roles;
}
I got error like
Cannot implicitly convert type
'System.Linq.IQueryable<Microsoft.AspNetCore.Identity.IdentityRole>' to
'System.Threading.Tasks.Task<System.Collections.Generic.List<Microsoft.AspNetCore.Identity.IdentityRole>>'.
An explicit conversion exists (are you missing a cast?)

I think that the problem is the return type you are using there.
From your code, I assume that _roleManager.Roles is of type System.Linq.IQueryable<Microsoft.AspNetCore.Identity.IdentityRole>.
Your return type is instead Task<List<IdentityRole>> or Task<IList<string>>
You can change the return type of your function to IQueryable as this:
public List<IdentityRole> AllUserRoles()
{
return _roleManager.Roles.ToList();
}
or do something like:
public Task<List<IdentityRole>> AllUserRoles()
{
return Task.FromResult(_roleManager.Roles.ToList());
}

Related

DbContext EntitySet null when entities are set to internal access

I want the db set to be internal in order to ensure external packages only have access to and program against the interface not the concrete class
e.g.
namespace Domain
{
public interface IProduct
{
string Description { get; }
int Id { get; }
decimal Price { get; }
}
}
//Separate Person.cs file for custom logic
namespace Domain
{
internal partial class Product :IProduct
{
}
}
internal partial class POS : DbContext
{
public POS()
: base("name=POS")
{
}
internal DbSet<Product> Products { get; set; }
}
//The other Person.cs file is generated by the .tt file
//_context.People is null which caused the dreaded null pointer exception :(
var people = _context.People.ToList();
As soon as I set the access to the Person class and People entity set to public via the Model Browser it works again, but I want to restrict the access to internal for package encapsulation.
It worked with Context in VS2010 EF but not with DbContext in VS2012.
Any help is much appreciated :}
P.S.
For now I have just edited the .tt file as below
public <#=code.Escape(container)#>()
: base("name=<#=container.Name#>")
{
Products = Set<Product>();
This generates the context class as below which instantiates the set, it would be nice to not have to add this to the .tt file for every entity set in the model.
internal partial class POS : DbContext
{
public POS()
: base("name=POS")
{
Products = Set<Product>();
}
I know this question is old but I just ran into this issue as well. According to a number of other StackOverflow posts, this is still the behavior of EntityFramework and the solution is still to explicitly Set<> the entity sets.
That said, instead of having to manually add each entity name to the .tt file, I created some code that will cause the TT file to automatically generate this code for each entity.
In the *.Context.tt file, you should spot the code for the constructor that looks something like this:
public <#=code.Escape(container)#>()
: base("name=<#=container.Name#>")
{
<#
if (!loader.IsLazyLoadingEnabled(container))
{
#>
this.Configuration.LazyLoadingEnabled = false;
<#
}
#>
}
Modify this so it now looks like:
public <#=code.Escape(container)#>()
: base("name=<#=container.Name#>")
{
<#
if (!loader.IsLazyLoadingEnabled(container))
{
#>
this.Configuration.LazyLoadingEnabled = false;
<#
}
#>
<#
foreach (var entitySet in container.BaseEntitySets.OfType<EntitySet>())
{
#>
<#=codeStringGenerator.SetStatement(entitySet)#>
<#
}
#>
}
Further down in the file you should see a class definition for the CodeStringGenerator class, add a new method (I added mine directly under the DbSet method definition around line 307):
public string SetStatement(EntitySet entitySet)
{
return string.Format(
CultureInfo.InvariantCulture,
"{0} = Set<{1}>();",
_code.Escape(entitySet),
_typeMapper.GetTypeName(entitySet.ElementType));
}
When you save the template it should regenerate the DbContext class with the Set<> statements for each entity in your model. New entities that are added will re-trigger the template generation and those new entities will also be included in the constructor.

How do I remove format from Linq property?

I´m building a Windows Forms aplication using LINQ to SQL. I´m using the auto generated code from the
dbml file.
Visual studio generated this code for the CNPJ property from my table:
[global::System.Data.Linq.Mapping.ColumnAttribute(Storage="_CNPJ", DbType="VarChar(20) NOT NULL", CanBeNull=false)]
public string CNPJ
{
get
{
return this._CNPJ;
}
set
{
if ((this._CNPJ != value))
{
this.OnCNPJChanging(value);
this.SendPropertyChanging();
this._CNPJ = value;
this.SendPropertyChanged("CNPJ");
this.OnCNPJChanged();
}
}
}
and what I wanted is this:
[global::System.Data.Linq.Mapping.ColumnAttribute(Storage="_CNPJ", DbType="VarChar(20) NOT NULL", CanBeNull=false)]
public string CNPJ
{
get
{
return APPLY_FORMAT(this._CNPJ);//Changed here
}
set
{
if ((this._CNPJ != value))
{
this.OnCNPJChanging(value);
this.SendPropertyChanging();
this._CNPJ = REMOVE_FORMAT(value); /// Changed here
this.SendPropertyChanged("CNPJ");
this.OnCNPJChanged();
}
}
}
But I will lose this changes when the code is re-generated.
Question is: what is the right way to accomplish this behavior (inherit and override, capture change event, other ) ?
if you´re curious, CNPJ is the brazilin business identification number, provided by the government.
Rather than trying to change the existing property, create a new property.
public partial class YourClass
{
public string FORMATTED_CNPJ
{
get
{
return APPLY_FORMAT(this._CNPJ);
}
set
{
this.CNPJ = REMOVE_FORMAT(value);
}
}
}
If you don't want anyone to access the underlying CNPJ property you can set it to private in the designer (the access modifier combobox in the column properties window). You can even rename that property to _CNPJ, make it private, and then name your 'wrapper' property above CNPJ if you want to avoid any breaking changes.
LINQ to SQL creates the classes as partial classes. You can create another partial class in a different file but with the same class name and then you can change the behaviour.
public partial class YourClass
{
partial void OnCNPJChanged()
{
this._CNPJ = REMOVE_FORMAT(value);
}
}
See here for more information.

Do i need to create automapper createmap both ways?

This might be a stupid question! (n00b to AutoMapper and time-short!)
I want to use AutoMapper to map from EF4 entities to ViewModel classes.
1) If I call
CreateMap<ModelClass, ViewModelClass>()
then do I also need to call
CreateMap<ViewModelClass, ModelClass>()
to perform the reverse?
2) If two classes have the same property names, then do I need a CreateMap statement at all, or is this just for "specific/custom" mappings?
For the info of the people who stumble upon this question. There appears to be now a built-in way to achieve a reverse mapping by adding a .ReverseMap() call at the end of your CreateMap() configuration chain.
In AutoMapper you have a Source type and a Destination type. So you will be able to map between this Source type and Destination type only if you have a corresponding CreateMap. So to answer your questions:
You don't need to define the reverse mapping. You have to do it only if you intend to map back.
Yes, you need to call CreateMap to indicate that those types are mappable otherwise an exception will be thrown when you call Map<TSource, TDest> telling you that a mapping doesn't exist between the source and destination type.
I've used an extension method do mapping both ways
public static IMappingExpression<TDestination, TSource> BothWays<TSource, TDestination>
(this IMappingExpression<TSource, TDestination> mappingExpression)
{
return Mapper.CreateMap<TDestination, TSource>();
}
usage:
CreateMap<Source, Dest>().BothWays();
Yes, or you can call CreateMap<ModelClass, ViewModelClass>().ReverseMap().
If two classes have same Member(Property,Field,GetMethod()), you needn't call CreateMap<TSrc,TDest>. Actually, if every member in TDest are all exist in TSrc, you needn't call CreateMap<TSrc,TDest>. The following code works.
class Person
{
public string Name { get; set; }
public int Age { get; set; }
}
class Person2
{
public string Name { get; set; }
public int? Age { get; set; }
public DateTime BirthTime { get; set; }
}
public class NormalProfile : Profile
{
public NormalProfile()
{
//CreateMap<Person2, Person>();//
}
}
var cfg = new MapperConfiguration(c =>
{
c.AddProfile<NormalProfile>();
});
//cfg.AssertConfigurationIsValid();
var mapper = cfg.CreateMapper();
var s3 = mapper.Map<Person>(new Person2 { Name = "Person2" });

Odd bug in C#4 compiler? Alias namespaces getting mixed up

Here's my issue,
I'm using a namespace to remove ambiguity from a factory class which is creating domain objects from entity framework entity objects (a POCO factory,.. if that makes sense!). Call me old fashioned but I like things this way :-)
The namespaces I'm working with are aliased as such -
using Entities = DataAccess.Models.AccessControl;
using Cases = DomainModel.BusinessObjects.Implimentations.Cases;
Now, the DomainModel.BusinessObjects.Implimentations.Cases namespace only has one type so far called CaseType. However whilst I was working on another type which consumes the CaseType class I noticed that when I 'dot' into the Cases alias, it points to a totally different namespace in my DataAccess assembly and gives me the CaseTypeFactory in intellisense.
So I checked the CaseType and CaseTypeFactory classes and they are namespaced correctly. What in god's name is going on? I really can't work this one out.
Here's the code for the CaseType and CaseTypeFactory if it helps.
CaseTypeFactory
using Domain = DomainModel.BusinessObjects.Implimentations.Cases;
using Entities = DataAccess.Models.AccessControl;
using Interfaces.DataAccess;
namespace DataAccess.Factories.Cases
{
public class CaseTypeFactory :
IEntityPOCOFactory<Domain.CaseType, Entities.CaseType>
{
#region IEntityPOCOFactory<CaseType,CaseType> Members
public Domain.CaseType CreatePOCO(Entities.CaseType entity)
{
return new Domain.CaseType(entity.Id, entity.Name, entity.LastChanged);
}
public IList<Domain.CaseType> CreatePOCOs(
IEnumerable<Entities.CaseType> entities)
{
var toReturn = new List<Domain.CaseType>();
foreach (var entity in entities)
{
toReturn.Add(CreatePOCO(entity));
}
return toReturn;
}
#endregion
}
}
CaseType
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using DomainModel.BusinessObjects.Base;
namespace DomainModel.BusinessObjects.Implimentations.Cases
{
public class CaseType : NamedNumberedAndVersioned
{
public CaseType(string name, DateTime lastChanged)
: this(0, name, lastChanged) { }
public CaseType(int id, string name, DateTime lastChanged)
: base(id, name, lastChanged) { }
public void Update(string name)
{
this.Name = name;
}
}
}
It's probably worth mentioning I'm working with .Net 4.0 / VS2010
Any help would be massively appreciated.
Thanks in advance.
Is the code you're writing in the DataAccess.Factories namespace? If so, then Cases will indeed resolve to DataAccess.Factories.Cases first.
Two options:
Use an alias which isn't also the name of another namespace, e.g.
using DomainCases = ...
Use :: instead of . to force it to use the alias:
IEntityPOCOFactory<Cases::CaseType, Whatever>
I'd personally go for the first option to make things clearer... or try to avoid requiring namespace aliases to start with.

InsertOnSubmit with interfaces (LINQ to SQL)

In our code we have:
public interface ILogMagazine
{
string Text { get; set; }
DateTime DateAndTime { get; set; }
string DetailMessage { get; set; }
}
SimpleDataContext: DataContext
{
public Table<ILogMagazine> LogMagaines
{
get { return GetTable<ILogMagazine>(); }
}
}
We try to:
DataContext db = new SimpleDataContext("...");
ILogMagazine lg = new LogMagazine()
{
Text = "test",
DateAndTime = DateTime.Now,
DetailMessage = "test",
};
db.LogMagazines.InsertOnSubmit(lg); // Exception thrown
db.SubmitChanges();
Exception: System.InvalidOperationException: The type 'DataLayer.ILogMagazine' is not mapped as a Table..
How we can solve this problem?
The error is because you haven't applied the [Table] attribute (normally it'd go on a class type, in your case the interface type), but I don't see it working even if you did. That's how the mapping is done- when you call GetTable, it looks for the Table attribute to know where to insert/query the data from.
That said, I'm pretty sure you can't do this with an interface. The type on GetTable has to be concrete, because it uses the generic arg passed (or inferred) on GetTable to know what object to create for a query. While it might technically be able to work for inserts, the same GetTable is used for both inserts and queries- which it most certainly won't work for. Same reason XmlSerializer and DataContractSerializer don't work with interfaces.
You'll always need a concrete type, but your entity types can still implement interfaces. I'm guessing you're trying to shuttle these around somewhere (service layer, perhaps), and you'll probably need to rethink that a bit.

Resources