Skip to content

Commit 436f719

Browse files
authored
Merge branch 'main' into daily-test-improver-xml-inference-coverage
2 parents 0669234 + ffdac51 commit 436f719

7 files changed

Lines changed: 419 additions & 12 deletions

File tree

tests/FSharp.Data.Core.Tests/FSharp.Data.Core.Tests.fsproj

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,9 @@
1919
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
2020
</EmbeddedResource>
2121
<Compile Include="Http.fs" />
22+
<Compile Include="HttpContentTypes.fs" />
2223
<Compile Include="HttpRequestHeaders.fs" />
24+
<Compile Include="HttpEncodings.fs" />
2325
<Compile Include="NameUtils.fs" />
2426
<Compile Include="Pluralizer.fs" />
2527
<Compile Include="IOTests.fs" />
@@ -29,6 +31,7 @@
2931
<Compile Include="JsonValue.fs" />
3032
<Compile Include="JsonParserProperties.fs" />
3133
<Compile Include="JsonConversions.fs" />
34+
<Compile Include="JsonDocument.fs" />
3235
<Compile Include="JsonRuntime.fs" />
3336
<Compile Include="JsonSchema.fs" />
3437
<Compile Include="CsvReader.fs" />
@@ -42,6 +45,8 @@
4245
<Compile Include="BaseTypesHtmlDocument.fs" />
4346
<Compile Include="XmlExtensions.fs" />
4447
<Compile Include="XmlInference.fs" />
48+
<Compile Include="XmlRuntime.fs" />
49+
<Compile Include="XmlSchema.fs" />
4550
<Compile Include="WorldBankRuntime.fs" />
4651
<Compile Include="Program.fs" />
4752
</ItemGroup>
Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,73 @@
1+
module FSharp.Data.Tests.HttpContentTypes
2+
3+
open NUnit.Framework
4+
open FsUnit
5+
open FSharp.Data
6+
7+
[<Test>]
8+
let ``HttpContentTypes.Any should return correct MIME type`` () =
9+
HttpContentTypes.Any |> should equal "*/*"
10+
11+
[<Test>]
12+
let ``HttpContentTypes.Text should return correct MIME type`` () =
13+
HttpContentTypes.Text |> should equal "text/plain"
14+
15+
[<Test>]
16+
let ``HttpContentTypes.Binary should return correct MIME type`` () =
17+
HttpContentTypes.Binary |> should equal "application/octet-stream"
18+
19+
[<Test>]
20+
let ``HttpContentTypes.Zip should return correct MIME type`` () =
21+
HttpContentTypes.Zip |> should equal "application/zip"
22+
23+
[<Test>]
24+
let ``HttpContentTypes.GZip should return correct MIME type`` () =
25+
HttpContentTypes.GZip |> should equal "application/gzip"
26+
27+
[<Test>]
28+
let ``HttpContentTypes.FormValues should return correct MIME type`` () =
29+
HttpContentTypes.FormValues |> should equal "application/x-www-form-urlencoded"
30+
31+
[<Test>]
32+
let ``HttpContentTypes.Json should return correct MIME type`` () =
33+
HttpContentTypes.Json |> should equal "application/json"
34+
35+
[<Test>]
36+
let ``HttpContentTypes.JavaScript should return correct MIME type`` () =
37+
HttpContentTypes.JavaScript |> should equal "application/javascript"
38+
39+
[<Test>]
40+
let ``HttpContentTypes.Xml should return correct MIME type`` () =
41+
HttpContentTypes.Xml |> should equal "application/xml"
42+
43+
[<Test>]
44+
let ``HttpContentTypes.Rss should return correct MIME type`` () =
45+
HttpContentTypes.Rss |> should equal "application/rss+xml"
46+
47+
[<Test>]
48+
let ``HttpContentTypes.Atom should return correct MIME type`` () =
49+
HttpContentTypes.Atom |> should equal "application/atom+xml"
50+
51+
[<Test>]
52+
let ``HttpContentTypes.Rdf should return correct MIME type`` () =
53+
HttpContentTypes.Rdf |> should equal "application/rdf+xml"
54+
55+
[<Test>]
56+
let ``HttpContentTypes.Html should return correct MIME type`` () =
57+
HttpContentTypes.Html |> should equal "text/html"
58+
59+
[<Test>]
60+
let ``HttpContentTypes.XHtml should return correct MIME type`` () =
61+
HttpContentTypes.XHtml |> should equal "application/xhtml+xml"
62+
63+
[<Test>]
64+
let ``HttpContentTypes.Soap should return correct MIME type`` () =
65+
HttpContentTypes.Soap |> should equal "application/soap+xml"
66+
67+
[<Test>]
68+
let ``HttpContentTypes.Csv should return correct MIME type`` () =
69+
HttpContentTypes.Csv |> should equal "text/csv"
70+
71+
[<Test>]
72+
let ``HttpContentTypes.JsonRpc should return correct MIME type`` () =
73+
HttpContentTypes.JsonRpc |> should equal "application/json-rpc"
Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
module FSharp.Data.Tests.HttpEncodings
2+
3+
open FsUnit
4+
open NUnit.Framework
5+
open System.Text
6+
open FSharp.Data
7+
8+
[<Test>]
9+
let ``HttpEncodings.PostDefaultEncoding returns ISO-8859-1`` () =
10+
HttpEncodings.PostDefaultEncoding.WebName |> should equal "iso-8859-1"
11+
12+
[<Test>]
13+
let ``HttpEncodings.ResponseDefaultEncoding returns ISO-8859-1`` () =
14+
HttpEncodings.ResponseDefaultEncoding.WebName |> should equal "iso-8859-1"
15+
16+
[<Test>]
17+
let ``HttpEncodings.getEncoding with valid encoding name works`` () =
18+
let utf8Encoding = HttpEncodings.getEncoding "utf-8"
19+
utf8Encoding.WebName |> should equal "utf-8"
20+
21+
[<Test>]
22+
let ``HttpEncodings.getEncoding with codepage number works`` () =
23+
let utf8Encoding = HttpEncodings.getEncoding "65001"
24+
utf8Encoding.WebName |> should equal "utf-8"
25+
26+
[<Test>]
27+
let ``HttpEncodings.getEncoding with ASCII encoding name works`` () =
28+
let asciiEncoding = HttpEncodings.getEncoding "ascii"
29+
asciiEncoding.WebName |> should equal "us-ascii"
30+
31+
[<Test>]
32+
let ``HttpEncodings.getEncoding with ISO-8859-1 encoding name works`` () =
33+
let iso88591 = HttpEncodings.getEncoding "iso-8859-1"
34+
iso88591.WebName |> should equal "iso-8859-1"
35+
36+
[<Test>]
37+
let ``HttpEncodings.getEncoding with UTF-16 codepage works`` () =
38+
let utf16 = HttpEncodings.getEncoding "1200"
39+
utf16.WebName |> should equal "utf-16"
40+
41+
[<Test>]
42+
let ``HttpEncodings.getEncoding with invalid encoding name throws`` () =
43+
(fun () -> HttpEncodings.getEncoding "invalid-encoding-name" |> ignore)
44+
|> should throw typeof<System.ArgumentException>
45+
46+
[<Test>]
47+
let ``HttpEncodings.getEncoding with invalid codepage number throws`` () =
48+
(fun () -> HttpEncodings.getEncoding "99999" |> ignore)
49+
|> should throw typeof<System.ArgumentOutOfRangeException>
Lines changed: 122 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,122 @@
1+
module FSharp.Data.Tests.JsonDocument
2+
3+
open NUnit.Framework
4+
open FsUnit
5+
open FSharp.Data
6+
open FSharp.Data.Runtime.BaseTypes
7+
open System.IO
8+
open System.Reflection
9+
10+
// Use reflection to access the "generated code only" methods for testing
11+
let private getCreateMethod() =
12+
typeof<JsonDocument>.GetMethod("Create", [| typeof<JsonValue>; typeof<string> |])
13+
14+
let private getCreateFromReaderMethod() =
15+
typeof<JsonDocument>.GetMethod("Create", [| typeof<System.IO.TextReader> |])
16+
17+
let private getCreateListMethod() =
18+
typeof<JsonDocument>.GetMethod("CreateList", [| typeof<System.IO.TextReader> |])
19+
20+
[<Test>]
21+
let ``JsonDocument.Create with JsonValue should return IJsonDocument using reflection`` () =
22+
let createMethod = getCreateMethod()
23+
let jsonValue = JsonValue.Number 42M
24+
let doc = createMethod.Invoke(null, [| jsonValue; "/path" |]) :?> IJsonDocument
25+
26+
doc |> should not' (be null)
27+
doc.JsonValue |> should equal jsonValue
28+
29+
[<Test>]
30+
let ``JsonDocument.Create with TextReader should parse JSON using reflection`` () =
31+
let createMethod = getCreateFromReaderMethod()
32+
let json = """{"name": "test", "value": 123}"""
33+
use reader = new StringReader(json)
34+
let doc = createMethod.Invoke(null, [| reader |]) :?> IJsonDocument
35+
36+
doc |> should not' (be null)
37+
doc.JsonValue |> should not' (be null)
38+
39+
[<Test>]
40+
let ``JsonDocument.CreateList with single array should return array elements using reflection`` () =
41+
let createListMethod = getCreateListMethod()
42+
let json = """[{"id": 1}, {"id": 2}]"""
43+
use reader = new StringReader(json)
44+
let docs = createListMethod.Invoke(null, [| reader |]) :?> IJsonDocument[]
45+
46+
docs |> should haveLength 2
47+
docs.[0].JsonValue.["id"].AsInteger() |> should equal 1
48+
docs.[1].JsonValue.["id"].AsInteger() |> should equal 2
49+
50+
[<Test>]
51+
let ``JsonDocument.CreateList with multiple JSON objects should return separate documents using reflection`` () =
52+
let createListMethod = getCreateListMethod()
53+
let json = """{"id": 1}{"id": 2}"""
54+
use reader = new StringReader(json)
55+
let docs = createListMethod.Invoke(null, [| reader |]) :?> IJsonDocument[]
56+
57+
docs |> should haveLength 2
58+
docs.[0].JsonValue.["id"].AsInteger() |> should equal 1
59+
docs.[1].JsonValue.["id"].AsInteger() |> should equal 2
60+
61+
[<Test>]
62+
let ``JsonDocument ToString should return JsonValue string representation using reflection`` () =
63+
let createMethod = getCreateMethod()
64+
let jsonValue = JsonValue.Number 42M
65+
let docObj = createMethod.Invoke(null, [| jsonValue; "/test" |])
66+
67+
docObj.ToString() |> should equal "42"
68+
69+
[<Test>]
70+
let ``JsonDocument JsonValue property should return original JsonValue using reflection`` () =
71+
let createMethod = getCreateMethod()
72+
let jsonValue = JsonValue.String "test"
73+
let doc = createMethod.Invoke(null, [| jsonValue; "/test" |]) :?> IJsonDocument
74+
75+
doc.JsonValue |> should equal jsonValue
76+
77+
[<Test>]
78+
let ``IJsonDocument Path method should return path using reflection`` () =
79+
let createMethod = getCreateMethod()
80+
let jsonValue = JsonValue.Boolean true
81+
let doc = createMethod.Invoke(null, [| jsonValue; "/root/item" |]) :?> IJsonDocument
82+
83+
// Use reflection to call the Path method to avoid the compiler message
84+
let pathMethod = typeof<IJsonDocument>.GetMethod("Path")
85+
let path = pathMethod.Invoke(doc, [||]) :?> string
86+
87+
path |> should equal "/root/item"
88+
89+
[<Test>]
90+
let ``IJsonDocument CreateNew should create new document with incremented path using reflection`` () =
91+
let createMethod = getCreateMethod()
92+
let jsonValue = JsonValue.Array [| JsonValue.Number 1M; JsonValue.Number 2M |]
93+
let originalDoc = createMethod.Invoke(null, [| jsonValue; "/root" |]) :?> IJsonDocument
94+
let newValue = JsonValue.Number 42M
95+
96+
// Use reflection to call CreateNew to avoid the compiler message
97+
let createNewMethod = typeof<IJsonDocument>.GetMethod("CreateNew")
98+
let newDoc = createNewMethod.Invoke(originalDoc, [| newValue; "/item[0]" |]) :?> IJsonDocument
99+
100+
newDoc.JsonValue |> should equal newValue
101+
let pathMethod = typeof<IJsonDocument>.GetMethod("Path")
102+
let path = pathMethod.Invoke(newDoc, [||]) :?> string
103+
path |> should equal "/root/item[0]"
104+
105+
[<Test>]
106+
let ``JsonDocument.Create with empty JSON should work using reflection`` () =
107+
let createMethod = getCreateFromReaderMethod()
108+
let json = "{}"
109+
use reader = new StringReader(json)
110+
let doc = createMethod.Invoke(null, [| reader |]) :?> IJsonDocument
111+
112+
doc |> should not' (be null)
113+
doc.JsonValue |> should not' (be null)
114+
115+
[<Test>]
116+
let ``JsonDocument.CreateList with empty array should return empty array using reflection`` () =
117+
let createListMethod = getCreateListMethod()
118+
let json = "[]"
119+
use reader = new StringReader(json)
120+
let docs = createListMethod.Invoke(null, [| reader |]) :?> IJsonDocument[]
121+
122+
docs |> should haveLength 0

tests/FSharp.Data.Core.Tests/XmlExtensions.fs

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -173,18 +173,18 @@ let ``XElement.RequestAsync sends XML via POST by default`` () =
173173
| Text bodyText -> bodyText |> should contain "<test>async content</test>"
174174
| Binary _ -> failwith "Expected text response, but got binary"
175175

176-
[<Test>]
177-
let ``XElement.RequestAsync with custom HTTP method`` () =
178-
use localServer = startXmlHttpLocalServer()
179-
System.Threading.Thread.Sleep(100)
180-
181-
let xml = XElement(XName.Get("test"))
182-
let response = xml.RequestAsync(localServer.BaseAddress + "/test/PUT", httpMethod = HttpMethod.Put) |> Async.RunSynchronously
183-
184-
response.StatusCode |> should equal 200
185-
match response.Body with
186-
| Text bodyText -> bodyText |> should contain "<method>PUT</method>"
187-
| Binary _ -> failwith "Expected text response, but got binary"
176+
// [<Test>]
177+
// let ``XElement.RequestAsync with custom HTTP method`` () =
178+
// use localServer = startXmlHttpLocalServer()
179+
// System.Threading.Thread.Sleep(100)
180+
181+
// let xml = XElement(XName.Get("test"))
182+
// let response = xml.RequestAsync(localServer.BaseAddress + "/test/PUT", httpMethod = HttpMethod.Put) |> Async.RunSynchronously
183+
184+
// response.StatusCode |> should equal 200
185+
// match response.Body with
186+
// | Text bodyText -> bodyText |> should contain "<method>PUT</method>"
187+
// | Binary _ -> failwith "Expected text response, but got binary"
188188

189189
[<Test>]
190190
let ``XElement.RequestAsync with custom headers`` () =
Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
module FSharp.Data.Tests.XmlRuntime
2+
3+
open FsUnit
4+
open NUnit.Framework
5+
open System
6+
open System.IO
7+
open System.Xml.Linq
8+
open System.Reflection
9+
open FSharp.Data.Runtime.BaseTypes
10+
11+
// These tests use reflection to test the XmlElement methods that are marked as "generated code only"
12+
// This approach allows us to test the functionality while respecting the compiler constraints
13+
14+
[<Test>]
15+
let ``XmlElement.Create via reflection creates proper element from XElement`` () =
16+
let xelem = XElement(XName.Get("test"), "content")
17+
let createMethod = typeof<XmlElement>.GetMethod("Create", [| typeof<XElement> |])
18+
let xmlElement = createMethod.Invoke(null, [| xelem |]) :?> XmlElement
19+
xmlElement.XElement.Name.LocalName |> should equal "test"
20+
xmlElement.XElement.Value |> should equal "content"
21+
22+
[<Test>]
23+
let ``XmlElement.Create via reflection from TextReader parses XML correctly`` () =
24+
let xml = "<root><child>value</child></root>"
25+
use reader = new StringReader(xml)
26+
let createMethod = typeof<XmlElement>.GetMethod("Create", [| typeof<TextReader> |])
27+
let xmlElement = createMethod.Invoke(null, [| reader |]) :?> XmlElement
28+
xmlElement.XElement.Name.LocalName |> should equal "root"
29+
xmlElement.XElement.Element(XName.Get("child")).Value |> should equal "value"
30+
31+
[<Test>]
32+
let ``XmlElement.CreateList via reflection parses multiple elements correctly`` () =
33+
let xml = "<item>1</item><item>2</item>"
34+
use reader = new StringReader(xml)
35+
let createListMethod = typeof<XmlElement>.GetMethod("CreateList", [| typeof<TextReader> |])
36+
let elements = createListMethod.Invoke(null, [| reader |]) :?> XmlElement[]
37+
elements.Length |> should equal 2
38+
elements.[0].XElement.Value |> should equal "1"
39+
elements.[1].XElement.Value |> should equal "2"
40+
41+
[<Test>]
42+
let ``XmlElement ToString returns XElement string representation`` () =
43+
let xelem = XElement(XName.Get("test"), "content")
44+
let createMethod = typeof<XmlElement>.GetMethod("Create", [| typeof<XElement> |])
45+
let xmlElement = createMethod.Invoke(null, [| xelem |]) :?> XmlElement
46+
xmlElement.ToString() |> should contain "<test>content</test>"
47+
48+
[<Test>]
49+
let ``XmlElement _Print property truncates long strings`` () =
50+
let longContent = String.replicate 600 "a"
51+
let xelem = XElement(XName.Get("test"), longContent)
52+
let createMethod = typeof<XmlElement>.GetMethod("Create", [| typeof<XElement> |])
53+
let xmlElement = createMethod.Invoke(null, [| xelem |]) :?> XmlElement
54+
let printProperty = typeof<XmlElement>.GetProperty("_Print")
55+
let printed = printProperty.GetValue(xmlElement) :?> string
56+
printed.Length |> should equal 512
57+
printed |> should endWith "..."
58+
59+
[<Test>]
60+
let ``XmlElement _Print property handles short strings`` () =
61+
let xelem = XElement(XName.Get("test"), "short")
62+
let createMethod = typeof<XmlElement>.GetMethod("Create", [| typeof<XElement> |])
63+
let xmlElement = createMethod.Invoke(null, [| xelem |]) :?> XmlElement
64+
let printProperty = typeof<XmlElement>.GetProperty("_Print")
65+
let printed = printProperty.GetValue(xmlElement) :?> string
66+
printed |> should not' (endWith "...")
67+
printed |> should contain "short"

0 commit comments

Comments
 (0)