Skip to content

Commit 54e8d0e

Browse files
committed
fixup! ObjectListFilter filter values to target type coercion (#589)
1 parent 9808e55 commit 54e8d0e

1 file changed

Lines changed: 54 additions & 23 deletions

File tree

tests/FSharp.Data.GraphQL.Tests/ObjectListFilter/ObjectListFilterComparerMappingTests.fs

Lines changed: 54 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -14,14 +14,21 @@ open FSharp.Data.GraphQL.Server.Middleware
1414

1515
[<Fact>]
1616
let ``comparerToStringComparison maps well-known StringComparer instances`` () =
17+
let currentCultureIsInvariant =
18+
obj.ReferenceEquals (StringComparer.CurrentCulture, StringComparer.InvariantCulture)
19+
1720
let testCases =
1821
[
19-
(StringComparer.OrdinalIgnoreCase :> IComparer, StringComparison.OrdinalIgnoreCase)
20-
(StringComparer.InvariantCultureIgnoreCase :> IComparer, StringComparison.InvariantCultureIgnoreCase)
21-
(StringComparer.CurrentCultureIgnoreCase :> IComparer, StringComparison.CurrentCultureIgnoreCase)
22-
(StringComparer.Ordinal :> IComparer, StringComparison.Ordinal)
23-
(StringComparer.InvariantCulture :> IComparer, StringComparison.InvariantCulture)
24-
(StringComparer.CurrentCulture :> IComparer, StringComparison.CurrentCulture)
22+
yield (StringComparer.OrdinalIgnoreCase :> IComparer, StringComparison.OrdinalIgnoreCase)
23+
yield (StringComparer.InvariantCultureIgnoreCase :> IComparer, StringComparison.InvariantCultureIgnoreCase)
24+
yield (StringComparer.Ordinal :> IComparer, StringComparison.Ordinal)
25+
yield (StringComparer.InvariantCulture :> IComparer, StringComparison.InvariantCulture)
26+
// On environments where CurrentCulture == InvariantCulture (e.g. Ubuntu CI with no locale),
27+
// StringComparer.Current* singletons ARE the same objects as StringComparer.Invariant*,
28+
// so they can only map to Invariant* values. Skip those cases in such environments.
29+
if not currentCultureIsInvariant then
30+
yield (StringComparer.CurrentCultureIgnoreCase :> IComparer, StringComparison.CurrentCultureIgnoreCase)
31+
yield (StringComparer.CurrentCulture :> IComparer, StringComparison.CurrentCulture)
2532
]
2633

2734
for comparer, expected in testCases do
@@ -34,14 +41,21 @@ let ``comparerToStringComparison maps well-known StringComparer instances`` () =
3441

3542
[<Fact>]
3643
let ``comparerToStringComparison singleton mappings are all distinct`` () =
44+
let currentCultureIsInvariant =
45+
obj.ReferenceEquals (StringComparer.CurrentCulture, StringComparer.InvariantCulture)
46+
47+
// On environments where CurrentCulture == InvariantCulture, Current* singletons are
48+
// the same objects as Invariant* ones, so distinctness can only be checked for the
49+
// remaining four singletons.
3750
let singletons : IComparer list =
3851
[
39-
StringComparer.OrdinalIgnoreCase
40-
StringComparer.InvariantCultureIgnoreCase
41-
StringComparer.CurrentCultureIgnoreCase
42-
StringComparer.Ordinal
43-
StringComparer.InvariantCulture
44-
StringComparer.CurrentCulture
52+
yield StringComparer.OrdinalIgnoreCase
53+
yield StringComparer.InvariantCultureIgnoreCase
54+
yield StringComparer.Ordinal
55+
yield StringComparer.InvariantCulture
56+
if not currentCultureIsInvariant then
57+
yield StringComparer.CurrentCultureIgnoreCase
58+
yield StringComparer.CurrentCulture
4559
]
4660

4761
let results =
@@ -53,9 +67,9 @@ let ``comparerToStringComparison singleton mappings are all distinct`` () =
5367

5468
// ─────────────────────────────────────────────────────────────────────────────
5569
// IsWellKnownCultureAwareComparer fallback path
56-
// StringComparer.Create produces a non-singleton comparer that is still
57-
// well-known, so it falls through the ReferenceEquals branch and hits the
58-
// IsWellKnownCultureAwareComparer fallback.
70+
// StringComparer.Create produces a non-singleton comparer; the singleton
71+
// ReferenceEquals fast path is skipped and IsWellKnownCultureAwareComparer
72+
// is used instead.
5973
// ─────────────────────────────────────────────────────────────────────────────
6074

6175
[<Fact>]
@@ -75,17 +89,30 @@ let ``comparerToStringComparison maps non-singleton InvariantCultureIgnoreCase c
7589

7690
[<Fact>]
7791
let ``comparerToStringComparison maps non-singleton CurrentCulture comparer`` () =
92+
// When CurrentCulture == InvariantCulture (e.g. Ubuntu CI), a non-singleton comparer
93+
// created from CurrentCulture is indistinguishable from InvariantCulture and will
94+
// legitimately map to InvariantCulture.
7895
let comparer = StringComparer.Create (CultureInfo.CurrentCulture, false) :> IComparer
7996
Assert.False (obj.ReferenceEquals (comparer, StringComparer.CurrentCulture :> obj))
8097
let result = ObjectListFilter.comparerToStringComparison comparer |> wantValueSome
81-
result |> equals StringComparison.CurrentCulture
98+
let currentCultureIsInvariant =
99+
CultureInfo.CurrentCulture.CompareInfo.Equals CultureInfo.InvariantCulture.CompareInfo
100+
let expected =
101+
if currentCultureIsInvariant then StringComparison.InvariantCulture
102+
else StringComparison.CurrentCulture
103+
result |> equals expected
82104

83105
[<Fact>]
84106
let ``comparerToStringComparison maps non-singleton CurrentCultureIgnoreCase comparer`` () =
85107
let comparer = StringComparer.Create (CultureInfo.CurrentCulture, true) :> IComparer
86108
Assert.False (obj.ReferenceEquals (comparer, StringComparer.CurrentCultureIgnoreCase :> obj))
87109
let result = ObjectListFilter.comparerToStringComparison comparer |> wantValueSome
88-
result |> equals StringComparison.CurrentCultureIgnoreCase
110+
let currentCultureIsInvariant =
111+
CultureInfo.CurrentCulture.CompareInfo.Equals CultureInfo.InvariantCulture.CompareInfo
112+
let expected =
113+
if currentCultureIsInvariant then StringComparison.InvariantCultureIgnoreCase
114+
else StringComparison.CurrentCultureIgnoreCase
115+
result |> equals expected
89116

90117
// ─────────────────────────────────────────────────────────────────────────────
91118
// Unknown / unsupported cases → ValueNone
@@ -122,14 +149,18 @@ let ``comparerToStringComparison returns ValueNone for non-standard culture comp
122149

123150
[<Fact>]
124151
let ``comparerToStringComparison is deterministic for singletons`` () =
152+
let currentCultureIsInvariant =
153+
obj.ReferenceEquals (StringComparer.CurrentCulture, StringComparer.InvariantCulture)
154+
125155
let singletons : IComparer list =
126156
[
127-
StringComparer.OrdinalIgnoreCase
128-
StringComparer.InvariantCultureIgnoreCase
129-
StringComparer.CurrentCultureIgnoreCase
130-
StringComparer.Ordinal
131-
StringComparer.InvariantCulture
132-
StringComparer.CurrentCulture
157+
yield StringComparer.OrdinalIgnoreCase
158+
yield StringComparer.InvariantCultureIgnoreCase
159+
yield StringComparer.Ordinal
160+
yield StringComparer.InvariantCulture
161+
if not currentCultureIsInvariant then
162+
yield StringComparer.CurrentCultureIgnoreCase
163+
yield StringComparer.CurrentCulture
133164
]
134165

135166
for comparer in singletons do

0 commit comments

Comments
 (0)