Skip to content

Commit d2b9d1f

Browse files
[Fusion] Add failing tests for selections below shared, non-refetchable field (#7950)
1 parent 1e3cf12 commit d2b9d1f

4 files changed

+528
-0
lines changed

src/HotChocolate/Fusion/test/Core.Tests/DemoIntegrationTests.cs

Lines changed: 231 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2341,6 +2341,237 @@ type ResaleSurveyFeedback {
23412341
await snapshot.MatchMarkdownAsync();
23422342
}
23432343

2344+
[Fact(Skip = "Fix this test in the new planner")]
2345+
public async Task Field_Below_Shared_Field_Only_Available_On_One_Subgraph_Type_Of_Shared_Field_Not_Node()
2346+
{
2347+
// arrange
2348+
var subgraph1 = await TestSubgraph.CreateAsync(
2349+
"""
2350+
interface Node {
2351+
id: ID!
2352+
}
2353+
type Product implements Node {
2354+
id: ID!
2355+
subgraph1Only: ProductAvailability
2356+
}
2357+
type ProductAvailability implements Node {
2358+
id: ID!
2359+
sharedLinked: ProductAvailabilityMail!
2360+
}
2361+
type ProductAvailabilityMail {
2362+
subgraph1Only: String!
2363+
}
2364+
type Query {
2365+
node("ID of the object." id: ID!): Node
2366+
productById(id: ID!): Product
2367+
productAvailabilityById(id: ID!): ProductAvailability
2368+
}
2369+
""");
2370+
2371+
var subgraph2 = await TestSubgraph.CreateAsync(
2372+
"""
2373+
interface Node {
2374+
id: ID!
2375+
}
2376+
type ProductAvailability implements Node {
2377+
id: ID!
2378+
sharedLinked: ProductAvailabilityMail!
2379+
}
2380+
type ProductAvailabilityMail {
2381+
subgraph2Only: Boolean!
2382+
}
2383+
type Query {
2384+
node("ID of the object." id: ID!): Node
2385+
productAvailabilityById(id: ID!): ProductAvailability
2386+
}
2387+
""");
2388+
2389+
using var subgraphs = new TestSubgraphCollection(output, [subgraph1, subgraph2]);
2390+
var executor = await subgraphs.GetExecutorAsync();
2391+
var request = OperationRequestBuilder.New()
2392+
.SetDocument(
2393+
"""
2394+
query($productId: ID!) {
2395+
productById(id: $productId) {
2396+
subgraph1Only {
2397+
sharedLinked {
2398+
subgraph2Only
2399+
}
2400+
}
2401+
}
2402+
}
2403+
""")
2404+
.SetVariableValues(new Dictionary<string, object?>
2405+
{
2406+
["productId"] = "UHJvZHVjdAppMzg2MzE4NTk="
2407+
})
2408+
.Build();
2409+
2410+
// act
2411+
var result = await executor.ExecuteAsync(request);
2412+
2413+
// assert
2414+
MatchMarkdownSnapshot(request, result);
2415+
}
2416+
2417+
[Fact(Skip = "Fix this test in the new planner")]
2418+
public async Task Field_Below_Shared_Field_Only_Available_On_One_Subgraph_Type_Of_Shared_Field_Not_Node_2()
2419+
{
2420+
// arrange
2421+
var subgraph1 = await TestSubgraph.CreateAsync(
2422+
"""
2423+
interface Node {
2424+
id: ID!
2425+
}
2426+
type Product implements Node {
2427+
id: ID!
2428+
subgraph1Only: ProductAvailability
2429+
}
2430+
type ProductAvailability implements Node {
2431+
id: ID!
2432+
sharedLinked: ProductAvailabilityMail!
2433+
}
2434+
type ProductAvailabilityMail {
2435+
sharedScalar: String!
2436+
}
2437+
type Query {
2438+
node("ID of the object." id: ID!): Node
2439+
productById(id: ID!): Product
2440+
productAvailabilityById(id: ID!): ProductAvailability
2441+
}
2442+
""");
2443+
2444+
var subgraph2 = await TestSubgraph.CreateAsync(
2445+
"""
2446+
interface Node {
2447+
id: ID!
2448+
}
2449+
type ProductAvailability implements Node {
2450+
sharedLinked: ProductAvailabilityMail!
2451+
subgraph2Only: Boolean!
2452+
id: ID!
2453+
}
2454+
type ProductAvailabilityMail {
2455+
subgraph2Only: Boolean!
2456+
sharedScalar: String!
2457+
}
2458+
type Query {
2459+
node("ID of the object." id: ID!): Node
2460+
productAvailabilityById(id: ID!): ProductAvailability
2461+
}
2462+
""");
2463+
2464+
using var subgraphs = new TestSubgraphCollection(output, [subgraph1, subgraph2]);
2465+
var executor = await subgraphs.GetExecutorAsync();
2466+
var request = OperationRequestBuilder.New()
2467+
.SetDocument(
2468+
"""
2469+
query($productId: ID!) {
2470+
productById(id: $productId) {
2471+
subgraph1Only {
2472+
subgraph2Only
2473+
sharedLinked {
2474+
subgraph2Only
2475+
sharedScalar
2476+
}
2477+
}
2478+
}
2479+
}
2480+
""")
2481+
.SetVariableValues(new Dictionary<string, object?>
2482+
{
2483+
["productId"] = "UHJvZHVjdAppMzg2MzE4NTk="
2484+
})
2485+
.Build();
2486+
2487+
// act
2488+
var result = await executor.ExecuteAsync(request);
2489+
2490+
// assert
2491+
MatchMarkdownSnapshot(request, result);
2492+
}
2493+
2494+
[Fact(Skip = "Fix this test in the new planner")]
2495+
public async Task Field_Below_Shared_Field_Only_Available_On_One_Subgraph_Type_Of_Shared_Field_Not_Node_3()
2496+
{
2497+
// arrange
2498+
var subgraph1 = await TestSubgraph.CreateAsync(
2499+
"""
2500+
interface Node {
2501+
id: ID!
2502+
}
2503+
type Product implements Node {
2504+
id: ID!
2505+
subgraph1Only: ProductAvailability
2506+
}
2507+
type ProductAvailability implements Node {
2508+
id: ID!
2509+
sharedLinked: ProductAvailabilityMail!
2510+
subgraph1Only: Boolean!
2511+
}
2512+
type ProductAvailabilityMail {
2513+
sharedScalar: String!
2514+
subgraph1Only: String!
2515+
}
2516+
type Query {
2517+
node("ID of the object." id: ID!): Node
2518+
productById(id: ID!): Product
2519+
productAvailabilityById(id: ID!): ProductAvailability
2520+
}
2521+
""");
2522+
2523+
var subgraph2 = await TestSubgraph.CreateAsync(
2524+
"""
2525+
interface Node {
2526+
id: ID!
2527+
}
2528+
type ProductAvailability implements Node {
2529+
sharedLinked: ProductAvailabilityMail!
2530+
subgraph2Only: Boolean!
2531+
id: ID!
2532+
}
2533+
type ProductAvailabilityMail {
2534+
subgraph2Only: Boolean!
2535+
sharedScalar: String!
2536+
}
2537+
type Query {
2538+
node("ID of the object." id: ID!): Node
2539+
productAvailabilityById(id: ID!): ProductAvailability
2540+
}
2541+
""");
2542+
2543+
using var subgraphs = new TestSubgraphCollection(output, [subgraph1, subgraph2]);
2544+
var executor = await subgraphs.GetExecutorAsync();
2545+
var request = OperationRequestBuilder.New()
2546+
.SetDocument(
2547+
"""
2548+
query($productId: ID!) {
2549+
productById(id: $productId) {
2550+
subgraph1Only {
2551+
subgraph2Only
2552+
subgraph1Only
2553+
sharedLinked {
2554+
subgraph2Only
2555+
sharedScalar
2556+
subgraph1Only
2557+
}
2558+
}
2559+
}
2560+
}
2561+
""")
2562+
.SetVariableValues(new Dictionary<string, object?>
2563+
{
2564+
["productId"] = "UHJvZHVjdAppMzg2MzE4NTk="
2565+
})
2566+
.Build();
2567+
2568+
// act
2569+
var result = await executor.ExecuteAsync(request);
2570+
2571+
// assert
2572+
MatchMarkdownSnapshot(request, result);
2573+
}
2574+
23442575
public sealed class HotReloadConfiguration : IObservable<GatewayConfiguration>
23452576
{
23462577
private GatewayConfiguration _configuration;
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,95 @@
1+
# Field_Below_Shared_Field_Only_Available_On_One_Subgraph_Type_Of_Shared_Field_Not_Node
2+
3+
## Result
4+
5+
```json
6+
{
7+
"data": {
8+
"productById": {
9+
"subgraph1Only": {
10+
"sharedLinked": {
11+
"subgraph2Only": true
12+
}
13+
}
14+
}
15+
}
16+
}
17+
```
18+
19+
## Request
20+
21+
```graphql
22+
query($productId: ID!) {
23+
productById(id: $productId) {
24+
subgraph1Only {
25+
sharedLinked {
26+
subgraph2Only
27+
}
28+
}
29+
}
30+
}
31+
```
32+
33+
## QueryPlan Hash
34+
35+
```text
36+
248A8F4DE404D0D21F7ABBC9255D2880DFDF4C2C
37+
```
38+
39+
## QueryPlan
40+
41+
```json
42+
{
43+
"document": "query($productId: ID!) { productById(id: $productId) { subgraph1Only { sharedLinked { subgraph2Only } } } }",
44+
"rootNode": {
45+
"type": "Sequence",
46+
"nodes": [
47+
{
48+
"type": "Resolve",
49+
"subgraph": "Subgraph_1",
50+
"document": "query fetch_productById_1($productId: ID!) { productById(id: $productId) { subgraph1Only { __fusion_exports__1: id } } }",
51+
"selectionSetId": 0,
52+
"provides": [
53+
{
54+
"variable": "__fusion_exports__1"
55+
}
56+
],
57+
"forwardedVariables": [
58+
{
59+
"variable": "productId"
60+
}
61+
]
62+
},
63+
{
64+
"type": "Compose",
65+
"selectionSetIds": [
66+
0
67+
]
68+
},
69+
{
70+
"type": "Resolve",
71+
"subgraph": "Subgraph_2",
72+
"document": "query fetch_productById_2($__fusion_exports__1: ID!) { productAvailabilityById(id: $__fusion_exports__1) { sharedLinked { subgraph2Only } } }",
73+
"selectionSetId": 2,
74+
"path": [
75+
"productAvailabilityById"
76+
],
77+
"requires": [
78+
{
79+
"variable": "__fusion_exports__1"
80+
}
81+
]
82+
},
83+
{
84+
"type": "Compose",
85+
"selectionSetIds": [
86+
2
87+
]
88+
}
89+
]
90+
},
91+
"state": {
92+
"__fusion_exports__1": "ProductAvailability_id"
93+
}
94+
}
95+
```

0 commit comments

Comments
 (0)