Skip to content

Commit 5554d1f

Browse files
xperiandriclaude
andcommitted
chore: lay the foundation for the per-collection modules
Prepares the chain of ADR 0001, one pull request per collection: - `Helper.fs` replaces `ImmutableCollectionUtil.fs` and adds `checkNotDefault`, which treats a default `ImmutableArray` as FSharp.Core treats a `null` array. - `build/check-order.fsx` checks that every signature file groups its functions under category banners in the canonical order, sorts them alphabetically inside a category and that the implementation file repeats that order. The FAKE target `CheckOrder` runs it before `DotnetBuild`. - The library and the tests target `net8.0` and `net10.0`; FSharp.Core 10.1.301 is the first release with `partitionWith`. - The placeholder tests are replaced by the category attributes of every collection, tests that enforce the category rules, and the shared helpers of the contract tests: inputs, the comparison of an exception with the FSharp.Core oracle, and the comparison of the `Option` and `Tuple` overrides with the default functions. - The README and the documentation pages list the collections in a table that each following pull request updates. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
1 parent 17f93b7 commit 5554d1f

24 files changed

Lines changed: 827 additions & 167 deletions

‎.github/copilot-instructions.md‎

Lines changed: 43 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -15,56 +15,71 @@
1515
```text
1616
/
1717
├── build/ – FAKE build scripts and release automation
18+
│ └── check-order.fsx – checks the category order of the signature files
1819
├── docsSrc/ – FSharp.Formatting documentation source
1920
├── src/FSharp.Collections.Immutable/ – main library
20-
│ ├── Helper.fs
21-
│ ├── ComputationExpressions.fs
21+
│ ├── Helper.fs – argument checks and exceptions shared by the modules
2222
│ ├── FlatList/ – ImmutableArray API surface and builders
23-
│ │ ├── FlatList.fs / FlatList.fsi
23+
│ │ ├── FlatList.fs / FlatList.fsi – includes the nested Parallel module
24+
│ │ ├── FlatListOption.fs / FlatListOption.fsi – Option namespace overrides
25+
│ │ ├── FlatListTuple.fs / FlatListTuple.fsi – Tuple namespace overrides
2426
│ │ ├── FlatListBuilder.fs
2527
│ │ └── FlatListCE.fs
2628
│ ├── IndexedList/ – ImmutableList API surface and builders
27-
│ │ ├── IIndexedList.fs / IIndexedList.fsi
28-
│ │ ├── IndexedList.fs / IndexedList.fsi
29+
│ │ ├── IndexedList.fs / IndexedList.fsi (+ Option / Tuple)
30+
│ │ ├── IIndexedList.fs / IIndexedList.fsi (+ Option / Tuple)
2931
│ │ ├── IndexedListBuilder.fs
3032
│ │ └── IndexedListCE.fs
3133
│ ├── Queue/ – ImmutableQueue API surface and CE
32-
│ │ ├── IQueue.fs / IQueue.fsi
33-
│ │ ├── Queue.fs / Queue.fsi
34+
│ │ ├── Queue.fs / Queue.fsi (+ Option / Tuple)
35+
│ │ ├── IQueue.fs / IQueue.fsi (+ Option / Tuple)
3436
│ │ └── QueueCE.fs
3537
│ ├── Stack/ – ImmutableStack API surface and CE
36-
│ │ ├── IStack.fs / IStack.fsi
37-
│ │ ├── Stack.fs / Stack.fsi
38+
│ │ ├── Stack.fs / Stack.fsi (+ Option / Tuple)
39+
│ │ ├── IStack.fs / IStack.fsi (+ Option / Tuple)
3840
│ │ └── StackCE.fs
3941
│ ├── HashMap/ – ImmutableDictionary API surface and CE
40-
│ │ ├── IHashMap.fs / IHashMap.fsi
41-
│ │ ├── HashMap.fs / HashMap.fsi
42+
│ │ ├── HashMap.fs / HashMap.fsi (+ Option / Tuple)
43+
│ │ ├── IMap.fs / IMap.fsi (+ Option / Tuple)
4244
│ │ └── HashMapCE.fs
4345
│ ├── SortedMap/ – ImmutableSortedDictionary API surface and CE
44-
│ │ ├── ISortedMap.fs / ISortedMap.fsi
45-
│ │ ├── SortedMap.fs / SortedMap.fsi
46+
│ │ ├── SortedMap.fs / SortedMap.fsi (+ Option / Tuple)
4647
│ │ └── SortedMapCE.fs
4748
│ ├── HashSet/ – ImmutableHashSet API surface and CE
48-
│ │ ├── IHashSet.fs / IHashSet.fsi
49-
│ │ ├── HashSet.fs / HashSet.fsi
49+
│ │ ├── HashSet.fs / HashSet.fsi (+ Option / Tuple)
50+
│ │ ├── ISet.fs / ISet.fsi (+ Option / Tuple)
5051
│ │ └── HashSetCE.fs
51-
│ └── SortedSet/ – ImmutableSortedSet API surface and CE
52-
│ ├── ISortedSet.fs / ISortedSet.fsi
53-
│ ├── SortedSet.fs / SortedSet.fsi
54-
│ └── SortedSetCE.fs
52+
│ ├── SortedSet/ – ImmutableSortedSet API surface and CE
53+
│ │ ├── SortedSet.fs / SortedSet.fsi (+ Option / Tuple)
54+
│ │ └── SortedSetCE.fs
55+
│ ├── FrozenMap/ – FrozenDictionary API surface and CE
56+
│ │ ├── FrozenMap.fs / FrozenMap.fsi (+ Option / Tuple)
57+
│ │ └── FrozenMapCE.fs
58+
│ ├── FrozenSet/ – FrozenSet API surface and CE
59+
│ │ ├── FrozenSet.fs / FrozenSet.fsi (+ Option / Tuple)
60+
│ │ └── FrozenSetCE.fs
61+
│ └── ComputationExpressions.fs – the computation expression instances
5562
└── tests/FSharp.Collections.Immutable.Tests/ – MSTest test project
56-
├── HelperTests.fs
5763
├── TestCategories.fs – centralized custom test category attributes
58-
├── FlatList/ – focused test files per operation group
59-
├── IndexedList/ – focused test files per operation group
60-
├── HashMap/ – focused test files per operation group
61-
├── SortedMap/ – focused test files per operation group
62-
├── HashSet/ – focused test files per operation group
63-
├── SortedSet/ – focused test files per operation group
64-
├── Queue/ – focused test files per operation group
65-
└── Stack/ – focused test files per operation group
64+
├── TestCategoriesTests.fs – enforces the test category rules
65+
├── Contracts/ – shared contract bases, inputs and assertion helpers
66+
└── <Collection>/ – ops records, contract classes, collection-specific,
67+
builder, computation expression, Option and Tuple tests
6668
```
6769

70+
The modules follow ADR 0001 – Per-collection modules (`docsSrc/Explanations/ADR_0001_Collection_Modules.md`):
71+
72+
* Each module groups its functions under banner comments `// ---- Category ----` in the order `Creation`, `Builder`,
73+
`Properties`, `Access`, `Search`, `Transformation`, `Folding`, `Partitioning and grouping`, `Sorting`, `Random`,
74+
`Conversion`, `Type-specific`, and sorts the functions of a category alphabetically (ordinal), active patterns last.
75+
The `.fs` file repeats the order of its `.fsi` file. `build/check-order.fsx` (FAKE target `CheckOrder`) enforces it.
76+
* `try*` functions return `voption`, tuples are struct tuples. The namespaces `FSharp.Collections.Immutable.Option` and
77+
`FSharp.Collections.Immutable.Tuple` repeat these functions with `option` results and reference tuples.
78+
* A function throws what the FSharp.Core function of the mirrored module throws for the same input: `Array` for
79+
`FlatList`, `List` for the other sequence-like modules, `Map` and `Set` for maps and sets.
80+
* Contract test bases in `Contracts/` take a record of the module's functions; a collection derives one test class per
81+
capability that it supports. Expected values and exceptions come from FSharp.Core.
82+
6883
## Libraries in Use
6984

7085
* [`System.Collections.Immutable`](https://www.nuget.org/packages/System.Collections.Immutable/) – immutable collections foundation

‎CHANGELOG.md‎

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,13 @@ All notable changes to this project will be documented in this file.
55
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
66
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
77

8+
## [Unreleased]
9+
10+
### Changed
11+
12+
* The package targets `net8.0` and `net10.0`.
13+
* The package requires FSharp.Core 10.1.301 or later, the first release with `partitionWith`.
14+
815
## [1.0.0] - 2020-02-23
916

1017
First release

‎Directory.Packages.props‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99
</ItemGroup>
1010
<ItemGroup Label="FSharp">
1111
<PackageVersion Include="FSharp.Control.Reactive" Version="6.1.2" />
12-
<PackageVersion Include="FSharp.Core" Version="10.0.100" />
12+
<PackageVersion Include="FSharp.Core" Version="10.1.301" />
1313
</ItemGroup>
1414
<ItemGroup Label="Build and Test">
1515
<PackageVersion Include="Argu" Version="6.2.5" />

‎README.md‎

Lines changed: 12 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -10,15 +10,17 @@ Please also join the [F# Open Source Group](http://fsharp.github.com)
1010

1111
## Features
1212

13-
* `FlatList` (`ImmutableArray`)
14-
* `ImmutableList`
15-
* `Stack` (`ImmutableStack`)
16-
* `Queue` (`ImmutableQueue`)
17-
* `HashMap` (`ImmutableDictionary`)
18-
* `SortedMap` (`ImmutableSortedDictionary`)
19-
* `HashSet` (`ImmutableHashSet`)
20-
* `SortedSet` (`ImmutableSortedSet`)
21-
* `IIndexedSeq` (`IReadOnlyList`)
13+
| Module | .NET type | Computation expression |
14+
|---|---|---|
15+
| `FlatList` | `ImmutableArray<'T>` | – |
16+
| `ImmutableList` | `ImmutableList<'T>` | – |
17+
| `Stack` | `ImmutableStack<'T>` | – |
18+
| `Queue` | `ImmutableQueue<'T>` | – |
19+
| `HashMap` | `ImmutableDictionary<'Key, 'Value>` | – |
20+
| `SortedMap` | `ImmutableSortedDictionary<'Key, 'Value>` | – |
21+
| `HashSet` | `ImmutableHashSet<'T>` | – |
22+
| `SortedSet` | `ImmutableSortedSet<'T>` | – |
23+
| `IIndexedSeq` | `IReadOnlyList<'T>` | – |
2224

2325
[Documentation](https://fsprojects.github.io/FSharp.Collections.Immutable/)
2426

@@ -85,6 +87,7 @@ or
8587
- `GitHubRelease` - Publishes a [GitHub Release](https://help.github.com/en/articles/creating-releases) with the Release Notes and any NuGet packages. Runs only from `Github Actions`.
8688
- `FormatCode` - Runs [Fantomas](https://github.com/fsprojects/fantomas) on the solution file.
8789
- `CheckFormatCode` - Runs [Fantomas --check](https://fsprojects.github.io/fantomas/docs/end-users/FormattingCheck.html) on the solution file.
90+
- `CheckOrder` - Runs `build/check-order.fsx`, which checks that every signature file groups its functions by category in the order of ADR 0001 and sorts them alphabetically inside a category. Runs before `DotnetBuild`.
8891
- `BuildDocs` - Generates [Documentation](https://fsprojects.github.io/FSharp.Formatting) from `docsSrc` and the [XML Documentation Comments](https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/xmldoc/) from your libraries in `src`.
8992
- `WatchDocs` - Generates documentation and starts a webserver locally. It will rebuild and hot reload if it detects any changes made to `docsSrc` files, or libraries in `src`.
9093

‎build/build.fs‎

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -163,6 +163,8 @@ module dotnet =
163163

164164
let fantomas args = DotNet.exec id "fantomas" args
165165

166+
let fsi args = tool id "fsi" args
167+
166168
module FSharpAnalyzers =
167169
type Arguments =
168170
| Project of string
@@ -588,6 +590,12 @@ let checkFormatCode ctx =
588590
else
589591
Trace.logf "Errors while formatting: %A" result.Errors
590592

593+
/// Checks the category banners and the alphabetical order of the functions in the signature files (ADR 0001, D4)
594+
let checkOrder _ =
595+
let script = rootDirectory </> "build" </> "check-order.fsx"
596+
let sourceDirectory = rootDirectory </> "src"
597+
dotnet.fsi $"\"%s{script}\" \"%s{sourceDirectory}\""
598+
591599

592600
let cleanDocsCache _ = DocsTool.cleanDocsCache ()
593601

@@ -651,6 +659,7 @@ let initTargets (ctx : Context.FakeExecutionContext) =
651659
Target.create "GitHubRelease" githubRelease
652660
Target.create "FormatCode" formatCode
653661
Target.create "CheckFormatCode" checkFormatCode
662+
Target.create "CheckOrder" checkOrder
654663
Target.create "Release" ignore // For local
655664
Target.create "Publish" ignore //For CI
656665
Target.create "CleanDocsCache" cleanDocsCache
@@ -698,6 +707,7 @@ let initTargets (ctx : Context.FakeExecutionContext) =
698707

699708

700709
"DotnetRestore" =?> ("CheckFormatCode", isCI.Value)
710+
==> "CheckOrder"
701711
==> "DotnetBuild"
702712
==> "DotnetTest"
703713
==> "DotnetPack"
@@ -708,6 +718,7 @@ let initTargets (ctx : Context.FakeExecutionContext) =
708718
"DotnetRestore"
709719
=?> ("CheckFormatCode", isCI.Value)
710720
=?> ("GenerateAssemblyInfo", isPublishToGitHub)
721+
==> "CheckOrder"
711722
==> "DotnetBuild"
712723
==> "DotnetTest"
713724
==> "DotnetPack"

0 commit comments

Comments
 (0)