[英]TempData null in asp.net core
我正在尝试在 asp.net 核心中使用 TempData 但是我在 TempData 的 get 方法上得到一个空值。 任何人都可以让我知道如何在 asp.net core 中使用 TempData
以下是我根据研究添加的内容。
项目.json 文件
{
"dependencies": {
"Microsoft.NETCore.App": {
"version": "1.0.1",
"type": "platform"
},
"Microsoft.AspNetCore.Mvc": "1.0.1",
"Microsoft.AspNetCore.Routing": "1.0.1",
"Microsoft.AspNetCore.Server.IISIntegration": "1.0.0",
"Microsoft.AspNetCore.Server.Kestrel": "1.0.1",
"Microsoft.Extensions.Configuration.EnvironmentVariables": "1.0.0",
"Microsoft.Extensions.Configuration.FileExtensions": "1.0.0",
"Microsoft.Extensions.Configuration.Json": "1.0.0",
"Microsoft.Extensions.Logging": "1.1.0",
"Microsoft.Extensions.Logging.Console": "1.0.0",
"Microsoft.Extensions.Logging.Debug": "1.0.0",
"Microsoft.Extensions.Options.ConfigurationExtensions": "1.0.0",
"Microsoft.EntityFrameworkCore.SqlServer": "1.1.0",
"Microsoft.EntityFrameworkCore.Tools": "1.1.0-preview4-final",
"Microsoft.EntityFrameworkCore.Design": "1.1.0",
"Microsoft.EntityFrameworkCore.SqlServer.Design": "1.1.0",
"DataBase": "1.0.0-*",
"UnitOfWork": "1.0.0-*",
"ViewModel": "1.0.0-*",
"Common": "1.0.0-*",
"System.IdentityModel.Tokens.Jwt": "5.0.0",
"Microsoft.AspNetCore.Authentication.JwtBearer": "1.0.0",
"Microsoft.AspNetCore.Diagnostics": "1.0.0",
"Microsoft.AspNetCore.StaticFiles": "1.0.0",
"Microsoft.AspNetCore.Session": "1.1.0",
"Microsoft.Extensions.Caching.Memory": "1.1.0"
},
"tools": {
"Microsoft.AspNetCore.Server.IISIntegration.Tools": "1.0.0-preview2-final",
"Microsoft.EntityFrameworkCore.Tools.DotNet": "1.0.0-preview3-final",
"Microsoft.AspNetCore.Razor.Tools": "1.0.0-preview2-final"
},
"frameworks": {
"netcoreapp1.0": {
"imports": [
"dotnet5.6",
"portable-net45+win8"
]
}
},
"buildOptions": {
"emitEntryPoint": true,
"preserveCompilationContext": true
},
"runtimeOptions": {
"configProperties": {
"System.GC.Server": true
}
},
"publishOptions": {
"include": [
"wwwroot",
"**/*.cshtml",
"appsettings.json",
"web.config"
]
},
"scripts": {
"postpublish": [ "dotnet publish-iis --publish-folder %publish:OutputPath% --framework %publish:FullTargetFramework%" ]
}
}
start.cs 文件
public void ConfigureServices(IServiceCollection services)
{
services.AddMemoryCache();
services.AddSession();
// Add framework services.
services.AddMvc();
services.AddTransient<IMarketUOW, MarketUow>();
services.AddTransient<ICategoryUow, CategoryUow>();
services.AddTransient<IUserProfileUow, UserProfileUow>();
services.AddTransient<IItemUow, ItemUow>();
services.AddTransient(typeof(IGenericRepository<>), typeof(GenericRepository<>));
var connection = Configuration.GetConnectionString("DefaultConnection");
services.AddDbContext<EmakitiContext>(options => options.UseSqlServer(connection));
}
public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
{
app.UseSession();
app.UseMvc(routes =>
{
routes.MapRoute(
name: "default",
template: "{controller=Home}/{action=Index}/{id?}");
});
}
这是 tempdata 的实现。调用此方法时,我可以看到 TempData 中的值。
[HttpGet("{pageNumber}")]
public GenericResponseObject<List<MarketViewModel>> GetMarketList(int pageNumber)
{
TempData["Currentpage"] = pageNumber;
TempData.Keep("Currentpage");
GenericResponseObject<List<MarketViewModel>> genericResponseObject = new GenericResponseObject<List<MarketViewModel>>();
genericResponseObject.IsSuccess = false;
genericResponseObject.Message = ConstaintStingValue.Tag_ConnectionFailed;
try
{
var marketItem = _iMarketUow.GetMarketList(pageNumber);
genericResponseObject.Data = marketItem.Item1;
var totalPages = (int)Math.Ceiling((decimal)marketItem.Item2 / (decimal)10);
genericResponseObject.TotalPage = totalPages;
genericResponseObject.IsSuccess = true;
genericResponseObject.Message = ConstaintStingValue.Tag_SuccessMessageRecord;
genericResponseObject.Message = ConstaintStingValue.Tag_ConnectionSuccess;
}
catch (Exception exception)
{
genericResponseObject.IsSuccess = false;
genericResponseObject.Message = exception.Message;
genericResponseObject.ErrorCode = exception.HResult;
genericResponseObject.ExceptionErrorMessage = exception.StackTrace;
}
return genericResponseObject;
}
但是下面的方法在临时数据中具有空值。
[HttpPost]
public GenericResponseObject<List<MarketViewModel>> AddUpdateMarket([FromBody] MarketViewModel marketViewModel)
{
GenericResponseObject<List<MarketViewModel>> genericResponseObject = new GenericResponseObject<List<MarketViewModel>>();
genericResponseObject.IsSuccess = false;
genericResponseObject.Message = ConstaintStingValue.Tag_ConnectionFailed;
if (marketViewModel!= null && ModelState.IsValid)
{
try
{
_iMarketUow.AddUpdateMarketList(marketViewModel);
genericResponseObject = GetMarketList(Convert.ToInt16(TempData.Peek("Currentpage")));
}
catch (Exception exception)
{
genericResponseObject.IsSuccess = false;
genericResponseObject.Message = exception.Message;
genericResponseObject.ErrorCode = exception.HResult;
genericResponseObject.ExceptionErrorMessage = exception.StackTrace;
}
}
else
{
genericResponseObject.Message = ConstaintStingValue.Tag_InputDataFormatNotMatch;
}
return genericResponseObject;
}
这是调试会话的图像
编辑:
如https://docs.microsoft.com/en-us/aspnet/core/security/gdpr?view=aspnetcore-2.2#tempdata-provider-and-session-state-cookies-arent-essential 中所述,默认情况下 TempData cookie由 CookiePolicy 中间件删除。 这可以通过将其放入 Startup.ConfigureServices() 来更改:
// The TempData provider cookie is not essential. Make it essential
// so TempData is functional when tracking is disabled.
services.Configure<CookieTempDataProviderOptions>(options => {
options.Cookie.IsEssential = true;
});
==============================================
旧答案:
迁移到 ASP Core 2.1 后,我遇到了这个问题,并在工作了一天后找到了解决方案:
在 Startup.Configure()
app.UseCookiePolicy();
应该在
app.UseMVC();
官方文档中描述的中间件顺序没有问题,即:
但是,当我们使用 Cookie 策略执行 (UseCookiePolicy) 时,只有将发送到浏览器的必要cookie 和来自 Tempdata 提供程序的 Cookie不是必需的,因此出现问题。 所以我们必须根据官方文档使它变得必不可少:
Tempdata 提供程序 cookie 不是必需的。 如果禁用跟踪,则 Tempdata 提供程序不起作用。 要在禁用跟踪时启用 Tempdata 提供程序,请在 Startup.ConfigureServices 中将 TempData cookie 标记为必需
// The Tempdata provider cookie is not essential. Make it essential
// so Tempdata is functional when tracking is disabled.
services.Configure<CookieTempDataProviderOptions>(options => {
options.Cookie.IsEssential = true;
});
添加这些行应该可以解决您的问题,而无需重新排序中间件。
请将您的所有软件包升级到相同的1.1.0
版本并添加缓存服务。 这是在Asp.Net Core
使用TempData
所需的东西
项目.json
"Microsoft.AspNetCore.Session": "1.1.0"
这是 Startup.cs 文件。 - 配置服务方法
public void ConfigureServices(IServiceCollection services)
{
services.AddMemoryCache();
services.AddSession();
services.AddMvc();
}
和配置方法。
public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
{
app.UseSession();
app.UseMvc(routes =>
{
routes.MapRoute(
name: "default",
template: "{controller=Home}/{action=Index}/{id?}");
});
}
现在尝试使用TempData
,它将起作用。
您可以使用 set ASPNETCORE_ENVIRONMENT=Development 环境变量设置环境。
聚苯乙烯
ASP.NET Core MVC
在Controller
上公开TempData
属性。 TempData
可用于存储仅需要在当前请求之后可用于单个请求的瞬态数据。
当读取TempDataDictionary
的对象时,它将在该请求结束时标记为删除。
Peek
和Keep
方法允许您读取值而不将其标记为删除。 假设我们回到将值保存到TempData
的第一个请求。
使用Peek
您只需一次调用即可获得该值,而无需将其标记为删除。
//second request, PEEK value so it is not deleted at the end of the request
object value = TempData.Peek("value");
//third request, read value and mark it for deletion
object value = TempData["value"];
使用Keep
您可以指定要保留的标记为删除的密钥。 检索对象并稍后将其从删除中保存是 2 个不同的调用。
//second request, get value marking it from deletion
object value = TempData["value"];
//later on decide to keep it
TempData.Keep("value");
//third request, read value and mark it for deletion
object value = TempData["value"];
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.