Move ResponseCacheFeature to new Abstractions package (#67)

Move ResponseCacheFeature to new Abstractions package and update package version numbers
This commit is contained in:
John Luo 2016-10-06 15:59:14 -07:00 committed by GitHub
parent 3b2a2eb892
commit 9d54cf1e8a
17 changed files with 131 additions and 84 deletions

View File

@ -20,6 +20,8 @@ Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "Microsoft.AspNetCore.Respon
EndProject
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "Microsoft.AspNetCore.ResponseCaching", "src\Microsoft.AspNetCore.ResponseCaching\Microsoft.AspNetCore.ResponseCaching.xproj", "{D1031270-DBD3-4F02-A3DC-3E7DADE8EBE6}"
EndProject
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "Microsoft.AspNetCore.ResponseCaching.Abstractions", "src\Microsoft.AspNetCore.ResponseCaching.Abstractions\Microsoft.AspNetCore.ResponseCaching.Abstractions.xproj", "{2D1022E8-CBB6-478D-A420-CB888D0EF7B7}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@ -38,6 +40,10 @@ Global
{D1031270-DBD3-4F02-A3DC-3E7DADE8EBE6}.Debug|Any CPU.Build.0 = Debug|Any CPU
{D1031270-DBD3-4F02-A3DC-3E7DADE8EBE6}.Release|Any CPU.ActiveCfg = Release|Any CPU
{D1031270-DBD3-4F02-A3DC-3E7DADE8EBE6}.Release|Any CPU.Build.0 = Release|Any CPU
{2D1022E8-CBB6-478D-A420-CB888D0EF7B7}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{2D1022E8-CBB6-478D-A420-CB888D0EF7B7}.Debug|Any CPU.Build.0 = Debug|Any CPU
{2D1022E8-CBB6-478D-A420-CB888D0EF7B7}.Release|Any CPU.ActiveCfg = Release|Any CPU
{2D1022E8-CBB6-478D-A420-CB888D0EF7B7}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
@ -46,5 +52,6 @@ Global
{1139BDEE-FA15-474D-8855-0AB91F23CF26} = {C51DF5BD-B53D-4795-BC01-A9AB066BF286}
{151B2027-3936-44B9-A4A0-E1E5902125AB} = {89A50974-E9D4-4F87-ACF2-6A6005E64931}
{D1031270-DBD3-4F02-A3DC-3E7DADE8EBE6} = {367AABAF-E03C-4491-A9A7-BDDE8903D1B4}
{2D1022E8-CBB6-478D-A420-CB888D0EF7B7} = {367AABAF-E03C-4491-A9A7-BDDE8903D1B4}
EndGlobalSection
EndGlobal

View File

@ -1,7 +1,7 @@
{
"version": "1.1.0-*",
"dependencies": {
"Microsoft.AspNetCore.ResponseCaching": "0.1.0-*",
"Microsoft.AspNetCore.ResponseCaching": "1.0.0-*",
"Microsoft.AspNetCore.Server.IISIntegration": "1.1.0-*",
"Microsoft.AspNetCore.Server.Kestrel": "1.1.0-*",
"Microsoft.Extensions.Caching.Memory": "1.1.0-*"

View File

@ -0,0 +1,18 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using Microsoft.Extensions.Primitives;
namespace Microsoft.AspNetCore.ResponseCaching
{
/// <summary>
/// A feature for configuring additional response cache options on the HTTP response.
/// </summary>
public interface IResponseCacheFeature
{
/// <summary>
/// Gets or sets the query keys used by the response cache middleware for calculating secondary vary keys.
/// </summary>
StringValues VaryByQueryKeys { get; set; }
}
}

View File

@ -0,0 +1,21 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="14.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup>
<VisualStudioVersion Condition="'$(VisualStudioVersion)' == ''">14.0</VisualStudioVersion>
<VSToolsPath Condition="'$(VSToolsPath)' == ''">$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)</VSToolsPath>
</PropertyGroup>
<Import Project="$(VSToolsPath)\DotNet\Microsoft.DotNet.Props" Condition="'$(VSToolsPath)' != ''" />
<PropertyGroup Label="Globals">
<ProjectGuid>2d1022e8-cbb6-478d-a420-cb888d0ef7b7</ProjectGuid>
<RootNamespace>Microsoft.AspNetCore.ResponseCaching.Abstractions</RootNamespace>
<BaseIntermediateOutputPath Condition="'$(BaseIntermediateOutputPath)'=='' ">.\obj</BaseIntermediateOutputPath>
<OutputPath Condition="'$(OutputPath)'=='' ">.\bin\</OutputPath>
<TargetFrameworkVersion>v4.5.2</TargetFrameworkVersion>
</PropertyGroup>
<PropertyGroup>
<SchemaVersion>2.0</SchemaVersion>
</PropertyGroup>
<Import Project="$(VSToolsPath)\DotNet\Microsoft.DotNet.targets" Condition="'$(VSToolsPath)' != ''" />
</Project>

View File

@ -0,0 +1,11 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Reflection;
using System.Resources;
[assembly: AssemblyMetadata("Serviceable", "True")]
[assembly: NeutralResourcesLanguage("en-us")]
[assembly: AssemblyCompany("Microsoft Corporation.")]
[assembly: AssemblyCopyright("© Microsoft Corporation. All rights reserved.")]
[assembly: AssemblyProduct("Microsoft ASP.NET Core")]

View File

@ -0,0 +1,31 @@
{
"version": "1.0.0-*",
"buildOptions": {
"warningsAsErrors": true,
"keyFile": "../../tools/Key.snk",
"xmlDoc": true
},
"description": "ASP.NET Core response caching middleware abstractions and feature interface definitions.",
"packOptions": {
"repository": {
"type": "git",
"url": "git://github.com/aspnet/ResponseCaching"
},
"tags": [
"aspnetcore",
"cache",
"caching"
]
},
"dependencies": {
"Microsoft.Extensions.Primitives": "1.1.0-*"
},
"frameworks": {
"net451": {},
"netstandard1.3": {
"dependencies": {
"NETStandard.Library": "1.6.1-*"
}
}
}
}

View File

@ -1,15 +0,0 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using Microsoft.AspNetCore.Http;
namespace Microsoft.AspNetCore.ResponseCaching
{
public static class ResponseCacheHttpContextExtensions
{
public static ResponseCacheFeature GetResponseCacheFeature(this HttpContext httpContext)
{
return httpContext.Features.Get<ResponseCacheFeature>();
}
}
}

View File

@ -1,25 +0,0 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using Microsoft.AspNetCore.Http;
namespace Microsoft.AspNetCore.ResponseCaching.Internal
{
internal static class InternalHttpContextExtensions
{
internal static void AddResponseCacheFeature(this HttpContext httpContext)
{
if (httpContext.GetResponseCacheFeature() != null)
{
throw new InvalidOperationException($"Another instance of {nameof(ResponseCacheFeature)} already exists. Only one instance of {nameof(ResponseCacheMiddleware)} can be configured for an application.");
}
httpContext.Features.Set(new ResponseCacheFeature());
}
internal static void RemoveResponseCacheFeature(this HttpContext httpContext)
{
httpContext.Features.Set<ResponseCacheFeature>(null);
}
}
}

View File

@ -5,7 +5,7 @@ using Microsoft.Extensions.Primitives;
namespace Microsoft.AspNetCore.ResponseCaching
{
public class ResponseCacheFeature
public class ResponseCacheFeature : IResponseCacheFeature
{
public StringValues VaryByQueryKeys { get; set; }
}

View File

@ -211,7 +211,7 @@ namespace Microsoft.AspNetCore.ResponseCaching
// Create the cache entry now
var response = context.HttpContext.Response;
var varyHeaders = new StringValues(response.Headers.GetCommaSeparatedValues(HeaderNames.Vary));
var varyQueryKeys = context.HttpContext.GetResponseCacheFeature()?.VaryByQueryKeys ?? StringValues.Empty;
var varyQueryKeys = context.HttpContext.Features.Get<IResponseCacheFeature>()?.VaryByQueryKeys ?? StringValues.Empty;
context.CachedResponseValidFor = context.ResponseCacheControlHeaderValue.SharedMaxAge ??
context.ResponseCacheControlHeaderValue.MaxAge ??
(context.ResponseExpires - context.ResponseTime.Value) ??
@ -325,7 +325,12 @@ namespace Microsoft.AspNetCore.ResponseCaching
context.HttpContext.Features.Set<IHttpSendFileFeature>(new SendFileFeatureWrapper(context.OriginalSendFileFeature, context.ResponseCacheStream));
}
context.HttpContext.AddResponseCacheFeature();
// Add IResponseCacheFeature
if (context.HttpContext.Features.Get<IResponseCacheFeature>() != null)
{
throw new InvalidOperationException($"Another instance of {nameof(ResponseCacheFeature)} already exists. Only one instance of {nameof(ResponseCacheMiddleware)} can be configured for an application.");
}
context.HttpContext.Features.Set<IResponseCacheFeature>(new ResponseCacheFeature());
}
internal static void UnshimResponseStream(ResponseCacheContext context)
@ -336,7 +341,8 @@ namespace Microsoft.AspNetCore.ResponseCaching
// Unshim IHttpSendFileFeature
context.HttpContext.Features.Set(context.OriginalSendFileFeature);
context.HttpContext.RemoveResponseCacheFeature();
// Remove IResponseCacheFeature
context.HttpContext.Features.Set<IResponseCacheFeature>(null);
}
internal static bool ContentIsNotModified(ResponseCacheContext context)

View File

@ -1,5 +1,5 @@
{
"version": "0.1.0-*",
"version": "1.0.0-*",
"buildOptions": {
"warningsAsErrors": true,
"allowUnsafe": true,
@ -24,6 +24,7 @@
"dependencies": {
"Microsoft.AspNetCore.Http": "1.1.0-*",
"Microsoft.AspNetCore.Http.Extensions": "1.1.0-*",
"Microsoft.AspNetCore.ResponseCaching.Abstractions": "1.0.0-*",
"Microsoft.Extensions.Caching.Memory": "1.1.0-*",
"Microsoft.Extensions.Logging.Abstractions": "1.1.0-*",
"Microsoft.Extensions.TaskCache.Sources": {

View File

@ -1,25 +0,0 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.ResponseCaching.Internal;
using Xunit;
namespace Microsoft.AspNetCore.ResponseCaching.Tests
{
public class HttpContextInternalExtensionTests
{
[Fact]
public void AddingSecondResponseCacheFeature_Throws()
{
var httpContext = new DefaultHttpContext();
// Should not throw
httpContext.AddResponseCacheFeature();
// Should throw
Assert.ThrowsAny<InvalidOperationException>(() => httpContext.AddResponseCacheFeature());
}
}
}

View File

@ -433,8 +433,10 @@ namespace Microsoft.AspNetCore.ResponseCaching.Tests
var context = TestUtils.CreateTestContext();
context.HttpContext.Response.Headers[HeaderNames.Vary] = new StringValues(new[] { "headerA", "HEADERB", "HEADERc" });
context.HttpContext.AddResponseCacheFeature();
context.HttpContext.GetResponseCacheFeature().VaryByQueryKeys = new StringValues(new[] { "queryB", "QUERYA" });
context.HttpContext.Features.Set<IResponseCacheFeature>(new ResponseCacheFeature()
{
VaryByQueryKeys = new StringValues(new[] { "queryB", "QUERYA" })
});
var cachedVaryByRules = new CachedVaryByRules()
{
Headers = new StringValues(new[] { "HeaderA", "HeaderB" }),
@ -462,8 +464,10 @@ namespace Microsoft.AspNetCore.ResponseCaching.Tests
var context = TestUtils.CreateTestContext();
context.HttpContext.Response.Headers[HeaderNames.Vary] = new StringValues(new[] { "headerA", "HEADERB" });
context.HttpContext.AddResponseCacheFeature();
context.HttpContext.GetResponseCacheFeature().VaryByQueryKeys = new StringValues(new[] { "queryB", "QUERYA" });
context.HttpContext.Features.Set<IResponseCacheFeature>(new ResponseCacheFeature()
{
VaryByQueryKeys = new StringValues(new[] { "queryB", "QUERYA" })
});
var cachedVaryByRules = new CachedVaryByRules()
{
VaryByKeyPrefix = FastGuid.NewGuid().IdString,
@ -669,6 +673,19 @@ namespace Microsoft.AspNetCore.ResponseCaching.Tests
LoggedMessage.ResponseNotCached);
}
[Fact]
public void ShimResponseStream_SecondInvocation_Throws()
{
var middleware = TestUtils.CreateTestMiddleware();
var context = TestUtils.CreateTestContext();
// Should not throw
middleware.ShimResponseStream(context);
// Should throw
Assert.ThrowsAny<InvalidOperationException>(() => middleware.ShimResponseStream(context));
}
[Fact]
public void GetOrderCasingNormalizedStringValues_NormalizesCasingToUpper()
{

View File

@ -104,7 +104,7 @@ namespace Microsoft.AspNetCore.ResponseCaching.Tests
{
var builders = TestUtils.CreateBuildersWithResponseCache(requestDelegate: async (context) =>
{
context.GetResponseCacheFeature().VaryByQueryKeys = "query";
context.Features.Get<IResponseCacheFeature>().VaryByQueryKeys = "query";
await TestUtils.TestRequestDelegate(context);
});
@ -126,7 +126,7 @@ namespace Microsoft.AspNetCore.ResponseCaching.Tests
{
var builders = TestUtils.CreateBuildersWithResponseCache(requestDelegate: async (context) =>
{
context.GetResponseCacheFeature().VaryByQueryKeys = new[] { "QueryA", "queryb" };
context.Features.Get<IResponseCacheFeature>().VaryByQueryKeys = new[] { "QueryA", "queryb" };
await TestUtils.TestRequestDelegate(context);
});
@ -148,7 +148,7 @@ namespace Microsoft.AspNetCore.ResponseCaching.Tests
{
var builders = TestUtils.CreateBuildersWithResponseCache(requestDelegate: async (context) =>
{
context.GetResponseCacheFeature().VaryByQueryKeys = new[] { "*" };
context.Features.Get<IResponseCacheFeature>().VaryByQueryKeys = new[] { "*" };
await TestUtils.TestRequestDelegate(context);
});
@ -170,7 +170,7 @@ namespace Microsoft.AspNetCore.ResponseCaching.Tests
{
var builders = TestUtils.CreateBuildersWithResponseCache(requestDelegate: async (context) =>
{
context.GetResponseCacheFeature().VaryByQueryKeys = new[] { "QueryB", "QueryA" };
context.Features.Get<IResponseCacheFeature>().VaryByQueryKeys = new[] { "QueryB", "QueryA" };
await TestUtils.TestRequestDelegate(context);
});
@ -192,7 +192,7 @@ namespace Microsoft.AspNetCore.ResponseCaching.Tests
{
var builders = TestUtils.CreateBuildersWithResponseCache(requestDelegate: async (context) =>
{
context.GetResponseCacheFeature().VaryByQueryKeys = new[] { "*" };
context.Features.Get<IResponseCacheFeature>().VaryByQueryKeys = new[] { "*" };
await TestUtils.TestRequestDelegate(context);
});
@ -214,7 +214,7 @@ namespace Microsoft.AspNetCore.ResponseCaching.Tests
{
var builders = TestUtils.CreateBuildersWithResponseCache(requestDelegate: async (context) =>
{
context.GetResponseCacheFeature().VaryByQueryKeys = "query";
context.Features.Get<IResponseCacheFeature>().VaryByQueryKeys = "query";
await TestUtils.TestRequestDelegate(context);
});
@ -236,7 +236,7 @@ namespace Microsoft.AspNetCore.ResponseCaching.Tests
{
var builders = TestUtils.CreateBuildersWithResponseCache(requestDelegate: async (context) =>
{
context.GetResponseCacheFeature().VaryByQueryKeys = new[] { "QueryA", "QueryB" };
context.Features.Get<IResponseCacheFeature>().VaryByQueryKeys = new[] { "QueryA", "QueryB" };
await TestUtils.TestRequestDelegate(context);
});
@ -258,7 +258,7 @@ namespace Microsoft.AspNetCore.ResponseCaching.Tests
{
var builders = TestUtils.CreateBuildersWithResponseCache(requestDelegate: async (context) =>
{
context.GetResponseCacheFeature().VaryByQueryKeys = new[] { "*" };
context.Features.Get<IResponseCacheFeature>().VaryByQueryKeys = new[] { "*" };
await TestUtils.TestRequestDelegate(context);
});

View File

@ -5,7 +5,7 @@
},
"dependencies": {
"dotnet-test-xunit": "2.2.0-*",
"Microsoft.AspNetCore.ResponseCaching": "0.1.0-*",
"Microsoft.AspNetCore.ResponseCaching": "1.0.0-*",
"Microsoft.AspNetCore.TestHost": "1.1.0-*",
"Microsoft.Extensions.Logging.Testing": "1.1.0-*",
"xunit": "2.2.0-*"