У меня проблема с кэшированием данных Entity Framework.А именно, у меня есть панель администрирования, в которой вы можете изменять роли пользователей и другие пользовательские данные, проблема в том, что мои службы возвращают пользователя со старыми данными.Чтобы быть еще хитрее, это происходит только при входе в систему.Я подозреваю, что это связано с созданием экземпляров DBContext и Unity DI.
Вот мои классы: Startup.cs
public void ConfigureAuth(IAppBuilder app)
{
// Configure the application for OAuth based flow
PublicClientId = "self";
var container = GlobalConfiguration.Configuration.DependencyResolver;
OAuthOptions = new OAuthAuthorizationServerOptions
{
TokenEndpointPath = new PathString("/api/users/token"),
Provider = new ApplicationOAuthProvider(PublicClientId,(IMembershipService)GlobalConfiguration.Configuration.DependencyResolver.GetService(typeof(IMembershipService))),
AuthorizeEndpointPath = new PathString("/api/users/login"),
AccessTokenExpireTimeSpan = TimeSpan.FromMinutes(30),
// In production mode set AllowInsecureHttp = false
AllowInsecureHttp = true
};
// Enable the application to use bearer tokens to authenticate users
app.UseOAuthBearerTokens(OAuthOptions);
}
public static void Register(HttpConfiguration config)
{
// security
config.SuppressDefaultHostAuthentication();
config.Filters.Add(new HostAuthenticationFilter(OAuthDefaults.AuthenticationType));
// routes
config.MapHttpAttributeRoutes();
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/{controller}/{id}",
defaults: new { id = RouteParameter.Optional }
);
var container = new UnityContainer();
container.RegisterType<TagModel>(new HierarchicalLifetimeManager());
container.RegisterType<IRoleRepo, RoleRepo>(new TransientLifetimeManager());
container.RegisterType<IUserRepo, UserRepo>(new TransientLifetimeManager());
container.RegisterType<IMembershipService, MembershipService>(new TransientLifetimeManager());
container.RegisterType<IEncryptionService, EncryptionService>(new TransientLifetimeManager());
IoC = container;
// SignalR dependency injection
config.DependencyResolver = new Unity.WebApi.UnityDependencyResolver(container);
var unityHubActivator = new UnityHubActivator(container);
GlobalHost.DependencyResolver.Register(typeof(IHubActivator), () => unityHubActivator);
// For more information, refer to: http://www.asp.net/web-api
config.EnableSystemDiagnosticsTracing();
config.EnsureInitialized();
}
ApplicationOAuthProvider.cs
public ApplicationOAuthProvider(string publicClientId,IMembershipService membershipService)
{
if (publicClientId == null)
{
throw new ArgumentNullException("publicClientId");
}
_publicClientId = publicClientId;
this.membershipService = membershipService;
}
public override async Task GrantResourceOwnerCredentials(OAuthGrantResourceOwnerCredentialsContext context)
{
User user = membershipService.ValidateUser(context.UserName, context.Password);
if (user == null)
{
context.SetError("invalid_grant", "Korisničko ime ili lozinka nisu ispravni.");
return;
}
ClaimsIdentity oAuthIdentity = new ClaimsIdentity(context.Options.AuthenticationType);
foreach (var role in user.roles)
{
oAuthIdentity.AddClaim(new Claim(ClaimTypes.Role, role.role_name));
}
oAuthIdentity.AddClaim(new Claim(ClaimTypes.NameIdentifier, user.username));
ClaimsIdentity cookiesIdentity = new ClaimsIdentity(context.Options.AuthenticationType);
AuthenticationProperties properties = CreateProperties(context.UserName,
Newtonsoft.Json.JsonConvert.SerializeObject(user.roles.Select(x => x.role_name)), user.Location.Naziv);
AuthenticationTicket ticket = new AuthenticationTicket(oAuthIdentity, properties);
ticket.Properties.AllowRefresh = true;
ticket.Properties.ExpiresUtc = DateTimeOffset.Now.AddMinutes(30);
context.Validated(ticket);
context.Request.Context.Authentication.SignIn(cookiesIdentity);
}
UserRepository.cs: EntityBaseRepo
public User GetSingleByUsername(string username)
{
return this.GetSingle(x => x.username == username, u => u.Location);
}
EntityBaseRepo.cs
public T GetSingle(Expression<Func<T, bool>> predicate, params Expression<Func<T, object>>[] includeProperties)
{
IQueryable<T> query = _context.Set<T>();
foreach (var includeProperty in includeProperties)
{
query = query.Include(includeProperty);
}
return query.Where(predicate).SingleOrDefault();
}
UserController.cs
public UserController(IMembershipService membershipService, IUserRepo userRepo,
ILocationRepo locationRepo, IRoleRepo roleRepo) {
this.membershipService = membershipService;
this.userRepo = userRepo;
this.roleRepo = roleRepo;
this.locationRepo = locationRepo;
}
public IHttpActionResult GetByUsername(string username, string password)
{
User user = membershipService.ValidateUser(username, password);
if (user == null) {
return BadRequest("Korisnik ne postoji.");
}
UserViewAdmin userView = AutoMapper.Mapper.Map<UserViewAdmin>(user);
return Ok(user);
}
Обратите внимание, когда я меняю роли или какое-либо другое свойство пользователяи пройти процесс входа в систему, я получаю старые данные, но когда я отправляю запрос в UserController, я получаю новые данные, даже если я использую тот же сервис для их получения.Может кто-нибудь объяснить, почему это происходит, и предложить какое-то решение?Спасибо
РЕДАКТИРОВАТЬ TagModel.cs (DBContext)
public TagModel() : base("name=TagModel")
{
Database.Log = x => Debug.WriteLine(x);
}
public virtual DbSet<Artikli> artiklis { get; set; }
public virtual DbSet<Permission> permissions { get; set; }
public virtual DbSet<Role> roles { get; set; }
public virtual DbSet<Tag> tags { get; set; }
public virtual DbSet<User> Users { get; set; }
public virtual DbSet<Location> Locations { get; set; }
public virtual DbSet<Reader> Readers { get; set; }
public virtual DbSet<Order> Orders { get; set; }
public virtual DbSet<Antenna> Antennas { get; set; }
public virtual DbSet<Printer> Printers { get; set; }
public virtual DbSet<TagLocation> TagLocations { get; set; }
public virtual DbSet<LocationArticle> LocationArticles { get; set; }
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Entity<Artikli>()
.HasKey(e => e.Id)
.Property(e => e.klasa_artikla)
.IsFixedLength();
modelBuilder.Entity<Reader>()
.HasKey(reader => reader.Id)
.HasMany(reader => reader.Antennas)
.WithRequired(antenna => antenna.Reader)
.HasForeignKey(antenna => antenna.ReaderFK)
.WillCascadeOnDelete(true);
modelBuilder.Entity<Antenna>()
.HasKey(pk => new {
pk.Id,
pk.ReaderFK
});
modelBuilder.Entity<Location>()
.HasKey(e => e.Id)
.HasMany(e => e.Readers)
.WithRequired(reader => reader.Location)
.HasForeignKey(reader => reader.LocationFK);
modelBuilder.Entity<Location>()
.HasKey(e => e.Id)
.HasMany(e => e.Printers)
.WithRequired(printer => printer.Location)
.HasForeignKey(printer => printer.LocationFK);
/*modelBuilder.Entity<Location>()
.HasKey(e => e.Id)
.HasMany(e => e.Tags)
.WithMany(e => e.Locations)
.Map(m => m.ToTable("storage_tags", "public"));
*/
modelBuilder.Entity<Tag>()
.HasKey(e=> e.Id);
modelBuilder.Entity<LocationArticle>()
.HasKey(e => e.Id);
modelBuilder.Entity<LocationArticle>()
.HasRequired(e => e.Location)
.WithMany(t => t.LocationArticles)
.HasForeignKey(e => e.LocationFK);
modelBuilder.Entity<LocationArticle>()
.HasRequired(e => e.Article)
.WithMany(t => t.LocationArticles)
.HasForeignKey(e => e.ArticleFK);
modelBuilder.Entity<TagLocation>()
.HasKey(e => e.Id);
modelBuilder.Entity<TagLocation>()
.HasRequired(e => e.Tag)
.WithMany(t => t.Locations)
.HasForeignKey(e => e.TagFK);
modelBuilder.Entity<TagLocation>()
.HasRequired(e => e.LocationArticle)
.WithMany(t => t.TagLocations)
.HasForeignKey(e => e.LocationArticleFK);
modelBuilder.Entity<Printer>()
.HasKey(e => e.Id);
modelBuilder.Entity<Storage>().Map(m =>
{
m.ToTable("storages", "public");
});
modelBuilder.Entity<Shop>().Map(m =>
{
m.ToTable("shops", "public");
});
modelBuilder.Entity<Order>()
.HasKey(e => e.Id)
.HasRequired(e => e.Source)
.WithMany(location => location.SentOrders)
.HasForeignKey(e => e.SourceFK);
modelBuilder.Entity<Order>()
.HasKey(e => e.Id)
.HasRequired(e => e.Destination)
.WithMany(location => location.RecievedOrders)
.HasForeignKey(e => e.DestinationFK);
modelBuilder.Entity<OrderTag>()
.HasKey(pk => new { pk.OrderFK, pk.TagFK, pk.ArticleFK })
.HasRequired(ot => ot.OrderArticle)
.WithMany(oa => oa.OrderTags)
.HasForeignKey(fk => new { fk.OrderFK, fk.ArticleFK})
.WillCascadeOnDelete(true);
modelBuilder.Entity<OrderTag>()
.HasKey(pk => new { pk.OrderFK, pk.TagFK, pk.ArticleFK })
.HasRequired(ot => ot.Tag)
.WithMany(t => t.Orders)
.HasForeignKey(ot => ot.TagFK);
modelBuilder.Entity<OrderArticle>()
.HasKey(pk => new { pk.OrderFK, pk.ArticleFK })
.HasRequired(oa => oa.Article)
.WithMany(a => a.OrderArticles)
.HasForeignKey(oa => oa.ArticleFK);
modelBuilder.Entity<OrderArticle>()
.HasKey(pk => new { pk.OrderFK, pk.ArticleFK })
.HasRequired(oa => oa.Order)
.WithMany(o => o.Articles)
.HasForeignKey(oa => oa.OrderFK);
modelBuilder.Entity<Artikli>()
.HasKey(e => e.Id)
.HasMany(e => e.LocationArticles)
.WithRequired(e => e.Article)
.HasForeignKey(e => e.ArticleFK)
.WillCascadeOnDelete(false);
modelBuilder.Entity<Permission>()
.HasKey(e => e.Id)
.HasMany(e => e.roles)
.WithMany(e => e.Permissions)
.Map(m => m.ToTable("role_permission", "public"));
modelBuilder.Entity<User>()
.HasKey(e => e.Id)
.HasRequired(e => e.Location)
.WithMany(location => location.Users)
.HasForeignKey(e => e.LocationFK);
modelBuilder.Entity<Role>()
.HasKey(e => e.Id)
.HasMany(e => e.Users)
.WithMany(e => e.roles)
.Map(m =>
{
m.MapLeftKey("role_role_id");
m.MapRightKey("user_user_id");
m.ToTable("user_role", "public");
});
}