Skip to content
This repository was archived by the owner on Dec 14, 2018. It is now read-only.

Commit ff6cbfd

Browse files
committed
Make saving TempData operate via a filter
This change moves the responsibility for saving TempData into a filter, which is registered with other View features. This moves TempData into the ViewFeatures package. ActionResults which require TempData to be kept use a new marker interface which is handled by the filter.
1 parent b5237b2 commit ff6cbfd

28 files changed

+257
-206
lines changed

src/Microsoft.AspNet.Mvc.Core/ControllerActionInvoker.cs

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,6 @@ public class ControllerActionInvoker : FilterActionInvoker
1818
private readonly ControllerActionDescriptor _descriptor;
1919
private readonly IControllerFactory _controllerFactory;
2020
private readonly IControllerActionArgumentBinder _argumentBinder;
21-
private readonly ITempDataDictionary _tempData;
2221

2322
public ControllerActionInvoker(
2423
[NotNull] ActionContext actionContext,
@@ -32,7 +31,6 @@ public ControllerActionInvoker(
3231
[NotNull] IReadOnlyList<IModelValidatorProvider> modelValidatorProviders,
3332
[NotNull] IReadOnlyList<IValueProviderFactory> valueProviderFactories,
3433
[NotNull] IScopedInstance<ActionBindingContext> actionBindingContextAccessor,
35-
[NotNull] ITempDataDictionary tempData,
3634
[NotNull] ILoggerFactory loggerFactory,
3735
int maxModelValidationErrors)
3836
: base(
@@ -50,7 +48,6 @@ public ControllerActionInvoker(
5048
_descriptor = descriptor;
5149
_controllerFactory = controllerFactory;
5250
_argumentBinder = controllerActionArgumentBinder;
53-
_tempData = tempData;
5451

5552
if (descriptor.MethodInfo == null)
5653
{
@@ -70,7 +67,6 @@ protected override object CreateInstance()
7067

7168
protected override void ReleaseInstance(object instance)
7269
{
73-
_tempData.Save();
7470
_controllerFactory.ReleaseController(instance);
7571
}
7672

src/Microsoft.AspNet.Mvc.Core/ControllerActionInvokerProvider.cs

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,6 @@ public class ControllerActionInvokerProvider : IActionInvokerProvider
2222
private readonly IReadOnlyList<IModelValidatorProvider> _modelValidatorProviders;
2323
private readonly IReadOnlyList<IValueProviderFactory> _valueProviderFactories;
2424
private readonly IScopedInstance<ActionBindingContext> _actionBindingContextAccessor;
25-
private readonly ITempDataDictionary _tempData;
2625
private readonly int _maxModelValidationErrors;
2726
private readonly ILoggerFactory _loggerFactory;
2827

@@ -32,7 +31,6 @@ public ControllerActionInvokerProvider(
3231
IControllerActionArgumentBinder argumentBinder,
3332
IOptions<MvcOptions> optionsAccessor,
3433
IScopedInstance<ActionBindingContext> actionBindingContextAccessor,
35-
ITempDataDictionary tempData,
3634
ILoggerFactory loggerFactory)
3735
{
3836
_controllerFactory = controllerFactory;
@@ -44,7 +42,6 @@ public ControllerActionInvokerProvider(
4442
_modelValidatorProviders = optionsAccessor.Options.ModelValidatorProviders.ToArray();
4543
_valueProviderFactories = optionsAccessor.Options.ValueProviderFactories.ToArray();
4644
_actionBindingContextAccessor = actionBindingContextAccessor;
47-
_tempData = tempData;
4845
_maxModelValidationErrors = optionsAccessor.Options.MaxModelValidationErrors;
4946
_loggerFactory = loggerFactory;
5047
}
@@ -73,7 +70,6 @@ public void OnProvidersExecuting([NotNull] ActionInvokerProviderContext context)
7370
_modelValidatorProviders,
7471
_valueProviderFactories,
7572
_actionBindingContextAccessor,
76-
_tempData,
7773
_loggerFactory,
7874
_maxModelValidationErrors);
7975
}

src/Microsoft.AspNet.Mvc.Core/DependencyInjection/MvcCoreServiceCollectionExtensions.cs

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -130,15 +130,6 @@ internal static void AddMvcCoreServices(IServiceCollection services)
130130
return new DefaultObjectValidator(options.ValidationExcludeFilters, modelMetadataProvider);
131131
}));
132132

133-
//
134-
// Temp Data
135-
//
136-
// Holds per-request data so it should be scoped
137-
services.TryAddScoped<ITempDataDictionary, TempDataDictionary>();
138-
139-
// This does caching so it should stay singleton
140-
services.TryAddSingleton<ITempDataProvider, SessionStateTempDataProvider>();
141-
142133
//
143134
// Random Infrastructure
144135
//
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
// Copyright (c) .NET Foundation. All rights reserved.
2+
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
3+
4+
namespace Microsoft.AspNet.Mvc
5+
{
6+
/// <summary>
7+
/// A marker interface for <see cref="IActionResult"/> types which need to have temp data saved.
8+
/// </summary>
9+
public interface IKeepTempDataResult : IActionResult
10+
{
11+
}
12+
}

src/Microsoft.AspNet.Mvc.Core/Properties/Resources.Designer.cs

Lines changed: 0 additions & 48 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/Microsoft.AspNet.Mvc.Core/RedirectResult.cs

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88

99
namespace Microsoft.AspNet.Mvc
1010
{
11-
public class RedirectResult : ActionResult
11+
public class RedirectResult : ActionResult, IKeepTempDataResult
1212
{
1313
private string _url;
1414

@@ -60,8 +60,6 @@ public override void ExecuteResult([NotNull] ActionContext context)
6060
destinationUrl = urlHelper.Content(Url);
6161
}
6262

63-
var tempData = context.HttpContext.RequestServices.GetRequiredService<ITempDataDictionary>();
64-
tempData.Keep();
6563
context.HttpContext.Response.Redirect(destinationUrl, Permanent);
6664
}
6765

src/Microsoft.AspNet.Mvc.Core/RedirectToActionResult.cs

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99

1010
namespace Microsoft.AspNet.Mvc
1111
{
12-
public class RedirectToActionResult : ActionResult
12+
public class RedirectToActionResult : ActionResult, IKeepTempDataResult
1313
{
1414
public RedirectToActionResult(
1515
string actionName,
@@ -51,8 +51,6 @@ public override void ExecuteResult([NotNull] ActionContext context)
5151
throw new InvalidOperationException(Resources.NoRoutesMatched);
5252
}
5353

54-
var tempData = context.HttpContext.RequestServices.GetRequiredService<ITempDataDictionary>();
55-
tempData.Keep();
5654
context.HttpContext.Response.Redirect(destinationUrl, Permanent);
5755
}
5856

src/Microsoft.AspNet.Mvc.Core/RedirectToRouteResult.cs

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99

1010
namespace Microsoft.AspNet.Mvc
1111
{
12-
public class RedirectToRouteResult : ActionResult
12+
public class RedirectToRouteResult : ActionResult, IKeepTempDataResult
1313
{
1414
public RedirectToRouteResult(object routeValues)
1515
: this(routeName: null, routeValues: routeValues)
@@ -51,8 +51,6 @@ public override void ExecuteResult([NotNull] ActionContext context)
5151
throw new InvalidOperationException(Resources.NoRoutesMatched);
5252
}
5353

54-
var tempData = context.HttpContext.RequestServices.GetRequiredService<ITempDataDictionary>();
55-
tempData.Keep();
5654
context.HttpContext.Response.Redirect(destinationUrl, Permanent);
5755
}
5856

src/Microsoft.AspNet.Mvc.Core/Resources.resx

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -288,15 +288,6 @@
288288
<data name="ModelType_WrongType" xml:space="preserve">
289289
<value>The model's runtime type '{0}' is not assignable to the type '{1}'.</value>
290290
</data>
291-
<data name="TempData_CannotSerializeToSession" xml:space="preserve">
292-
<value>The '{0}' cannot serialize an object of type '{1}' to session state.</value>
293-
</data>
294-
<data name="TempData_CannotDeserializeToken" xml:space="preserve">
295-
<value>Cannot deserialize {0} of type '{1}'.</value>
296-
</data>
297-
<data name="TempData_CannotSerializeDictionary" xml:space="preserve">
298-
<value>The '{0}' cannot serialize a dictionary with a key of type '{1}' to session state.</value>
299-
</data>
300291
<data name="ValueInterfaceAbstractOrOpenGenericTypesCannotBeActivated" xml:space="preserve">
301292
<value>The type '{0}' cannot be activated by '{1}' because it is either a value type, an interface, an abstract class or an open generic type.</value>
302293
</data>

src/Microsoft.AspNet.Mvc.Core/project.json

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,15 +14,15 @@
1414
"Microsoft.AspNet.Hosting.Abstractions": "1.0.0-*",
1515
"Microsoft.AspNet.Http": "1.0.0-*",
1616
"Microsoft.AspNet.Mvc.Abstractions": "6.0.0-*",
17+
"Microsoft.Dnx.Runtime.Abstractions": "1.0.0-*",
1718
"Microsoft.Framework.ClosedGenericMatcher.Sources": { "version": "1.0.0-*", "type": "build" },
1819
"Microsoft.Framework.Logging.Abstractions": "1.0.0-*",
1920
"Microsoft.Framework.Notification": "1.0.0-*",
2021
"Microsoft.Framework.NotNullAttribute.Sources": { "version": "1.0.0-*", "type": "build" },
2122
"Microsoft.Framework.PropertyActivator.Sources": { "version": "1.0.0-*", "type": "build" },
2223
"Microsoft.Framework.PropertyHelper.Sources": { "version": "1.0.0-*", "type": "build" },
23-
"Microsoft.Framework.SecurityHelper.Sources": { "version": "1.0.0-*", "type": "build" },
24-
"Microsoft.Dnx.Compilation.Abstractions": "1.0.0-*",
25-
"Newtonsoft.Json": "6.0.6"
24+
"Microsoft.Framework.SecurityHelper.Sources": { "version": "1.0.0-*", "type": "build" }
25+
2626
},
2727
"frameworks": {
2828
"dnx451": { },

src/Microsoft.AspNet.Mvc.ViewFeatures/DependencyInjection/MvcViewFeaturesMvcBuilderExtensions.cs

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,8 @@ internal static void AddViewServices(IServiceCollection services)
5151

5252
services.TryAddEnumerable(
5353
ServiceDescriptor.Transient<IConfigureOptions<MvcViewOptions>, MvcViewOptionsSetup>());
54+
services.TryAddEnumerable(
55+
ServiceDescriptor.Transient<IConfigureOptions<MvcOptions>, TempDataMvcOptionsSetup>());
5456

5557
//
5658
// View Engine and related infrastructure
@@ -95,6 +97,16 @@ internal static void AddViewServices(IServiceCollection services)
9597
services.TryAddTransient<IViewComponentDescriptorProvider, DefaultViewComponentDescriptorProvider>();
9698
services.TryAddSingleton<IViewComponentInvokerFactory, DefaultViewComponentInvokerFactory>();
9799
services.TryAddTransient<IViewComponentHelper, DefaultViewComponentHelper>();
100+
101+
//
102+
// Temp Data
103+
//
104+
// Holds per-request data so it should be scoped
105+
services.TryAddScoped<ITempDataDictionary, TempDataDictionary>();
106+
services.TryAddScoped<SaveTempDataFilter>();
107+
108+
// This does caching so it should stay singleton
109+
services.TryAddSingleton<ITempDataProvider, SessionStateTempDataProvider>();
98110
}
99111
}
100112
}

src/Microsoft.AspNet.Mvc.ViewFeatures/Properties/Resources.Designer.cs

Lines changed: 48 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/Microsoft.AspNet.Mvc.ViewFeatures/Resources.resx

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -265,4 +265,13 @@
265265
<data name="ViewComponentResult_NameOrTypeMustBeSet" xml:space="preserve">
266266
<value>Either the '{0}' or '{1}' property must be set in order to invoke a view component.</value>
267267
</data>
268+
<data name="TempData_CannotDeserializeToken" xml:space="preserve">
269+
<value>Cannot deserialize {0} of type '{1}'.</value>
270+
</data>
271+
<data name="TempData_CannotSerializeDictionary" xml:space="preserve">
272+
<value>The '{0}' cannot serialize a dictionary with a key of type '{1}' to session state.</value>
273+
</data>
274+
<data name="TempData_CannotSerializeToSession" xml:space="preserve">
275+
<value>The '{0}' cannot serialize an object of type '{1}' to session state.</value>
276+
</data>
268277
</root>
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
// Copyright (c) .NET Foundation. All rights reserved.
2+
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
3+
4+
using System;
5+
using Microsoft.Framework.DependencyInjection;
6+
7+
namespace Microsoft.AspNet.Mvc
8+
{
9+
/// <summary>
10+
/// Adds a filter which will save the <see cref="ITempDataDictionary"/> for a request.
11+
/// </summary>
12+
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, AllowMultiple = false, Inherited = true)]
13+
public class SaveTempDataAttribute : Attribute, IFilterFactory
14+
{
15+
/// <inheritdoc />
16+
public IFilterMetadata CreateInstance(IServiceProvider serviceProvider)
17+
{
18+
return serviceProvider.GetRequiredService<SaveTempDataFilter>();
19+
}
20+
}
21+
}

0 commit comments

Comments
 (0)