Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Fixed cache control defaults were not reliably applied (#5732)
- Loading branch information
1 parent
a7d1279
commit d4f7c5b
Showing
11 changed files
with
163 additions
and
57 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
66 changes: 66 additions & 0 deletions
66
src/HotChocolate/Caching/test/Caching.Tests/SchemaTests.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,66 @@ | ||
using System.Threading.Tasks; | ||
using CookieCrumble; | ||
using HotChocolate.Execution; | ||
using HotChocolate.Types; | ||
using Microsoft.Extensions.DependencyInjection; | ||
using Xunit; | ||
|
||
namespace HotChocolate.Caching.Tests; | ||
|
||
public class SchemaTests | ||
{ | ||
[Fact] | ||
public async Task Allow_CacheControl_On_FieldDefinition() | ||
{ | ||
var schema = | ||
await new ServiceCollection() | ||
.AddGraphQLServer() | ||
.AddTypeExtension(typeof(Query)) | ||
.ConfigureSchema( | ||
b => b.TryAddRootType( | ||
() => new ObjectType( | ||
d => d.Name(OperationTypeNames.Query)), | ||
Language.OperationType.Query)) | ||
.AddCacheControl() | ||
.BuildSchemaAsync(); | ||
|
||
schema.MatchInlineSnapshot( | ||
""" | ||
schema { | ||
query: Query | ||
} | ||
|
||
type Book { | ||
title: String! @cacheControl(maxAge: 5000) | ||
description: String! | ||
} | ||
|
||
type Query { | ||
book: Book! @cacheControl(maxAge: 0) | ||
} | ||
|
||
"The scope of a cache hint." | ||
enum CacheControlScope { | ||
"The value to cache is not tied to a single user." | ||
PUBLIC | ||
"The value to cache is specific to a single user." | ||
PRIVATE | ||
} | ||
|
||
"The `@cacheControl` directive may be provided for individual fields or entire object, interface or union types to provide caching hints to the executor." | ||
directive @cacheControl("The maximum amount of time this field's cached value is valid, in seconds." maxAge: Int "If `PRIVATE`, the field's value is specific to a single user. The default value is `PUBLIC`, which means the field's value is not tied to a single user." scope: CacheControlScope "If `true`, the field inherits the `maxAge` of its parent field." inheritMaxAge: Boolean) on OBJECT | FIELD_DEFINITION | INTERFACE | UNION | ||
"""); | ||
} | ||
|
||
[QueryType] | ||
public static class Query | ||
{ | ||
public static Book GetBook() | ||
=> new Book("C# in depth.", "abc"); | ||
|
||
} | ||
|
||
public record Book( | ||
[property: CacheControl(5000)] string Title, | ||
string Description); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
43 changes: 43 additions & 0 deletions
43
src/HotChocolate/Core/src/Types/Types/StaticObjectTypeExtension.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
#nullable enable | ||
using System; | ||
using HotChocolate.Types.Descriptors; | ||
|
||
namespace HotChocolate.Types; | ||
|
||
/// <summary> | ||
/// This helper class is used to allow static type extensions. | ||
/// </summary> | ||
internal sealed class StaticObjectTypeExtension : ObjectTypeExtension | ||
{ | ||
private readonly Type _staticExtType; | ||
|
||
public StaticObjectTypeExtension(Type staticExtType) | ||
=> _staticExtType = staticExtType; | ||
|
||
protected override void Configure(IObjectTypeDescriptor descriptor) | ||
{ | ||
var context = descriptor.Extend().Context; | ||
var definition = descriptor.Extend().Definition; | ||
|
||
// we are using the non-generic type extension class which would set nothing. | ||
definition.Name = context.Naming.GetTypeName(_staticExtType, TypeKind.Object); | ||
definition.Description = context.Naming.GetTypeDescription(_staticExtType, TypeKind.Object); | ||
definition.Fields.BindingBehavior = context.Options.DefaultBindingBehavior; | ||
definition.FieldBindingFlags = context.Options.DefaultFieldBindingFlags; | ||
definition.FieldBindingType = _staticExtType; | ||
definition.IsExtension = true; | ||
|
||
// we set the static type as runtime type. Since this is not the actual runtime | ||
// type and is replaced by the actual runtime type of the GraphQL type | ||
// we do not run into any conflicts here. | ||
definition.RuntimeType = _staticExtType; | ||
|
||
// next we set the binding flags to only infer static members. | ||
definition.FieldBindingFlags = FieldBindingFlags.Static; | ||
|
||
// last we use an internal helper to force infer the GraphQL fields from the | ||
// field binding type which is at this moment the runtime type that we have | ||
// set above. | ||
((ObjectTypeDescriptor)descriptor).InferFieldsFromFieldBindingType(); | ||
} | ||
} |