wip: nixifying Fornix build pipeline

This commit is contained in:
2025-12-10 14:06:35 +01:00
parent 209b963319
commit 89aecb6609
18 changed files with 771 additions and 322 deletions

3
.gitignore vendored
View File

@@ -96,3 +96,6 @@ build/
*.db
build.fsx.lock
_*.yaml
result
result-*

View File

@@ -1,8 +1,33 @@
variables:
PROJECT_NAME: fornix
SKIP_TESTS: "true"
stages:
- build
- release
include:
- project: oceanbox/gitlab-ci
ref: v3
file: DotnetDeployment.gitlab-ci.yml
build-job:
stage: build
tags:
- nix
script:
- echo "Building..."
- nix-build -A default
- echo "Build done."
release-job:
stage: release
tags:
- nix
variables:
IMAGE_TAG: $CI_REGISTRY_IMAGE:$CI_COMMIT_REF_SLUG
rules:
- if: $CI_COMMIT_REF_NAME == $CI_DEFAULT_BRANCH
variables:
IMAGE_TAG: $CI_REGISTRY_IMAGE:debug-$CI_COMMIT_SHORT_SHA
- if: $CI_COMMIT_TAG
variables:
IMAGE_TAG: $CI_REGISTRY_IMAGE:$CI_COMMIT_TAG
script:
- echo "Building container..."
- nix-build -A container
- echo "Deploying application..."
- echo "$CI_REGISTRY_PASSWORD" | skopeo login $CI_REGISTRY -u $CI_REGISTRY_USER --password-stdin
- skopeo copy --insecure-policy docker-archive:result docker://$IMAGE_TAG
- echo "Container successfully released."

7
Fornix.slnx Normal file
View File

@@ -0,0 +1,7 @@
<Solution>
<Folder Name="/src/">
<Project Path="src/Client/Client.fsproj" />
<Project Path="src/Server/Server.fsproj" />
<Project Path="src/Shared/Shared.fsproj" />
</Folder>
</Solution>

1
VERSION Normal file
View File

@@ -0,0 +1 @@
1.0.0

87
default.nix Normal file
View File

@@ -0,0 +1,87 @@
{
sources ? import ./nix,
system ? builtins.currentSystem,
pkgs ? import sources.nixpkgs {
inherit system;
config = { };
overlays = [ ];
},
env ? "Debug",
nix-utils ? import sources.nix-utils { },
}:
let
version =
let
clean = pkgs.lib.removeSuffix "\n";
version = builtins.readFile ./VERSION;
in
clean version;
dotnet-sdk = pkgs.dotnetCorePackages.sdk_10_0;
dotnet-runtime = pkgs.dotnetCorePackages.aspnetcore_10_0;
deps = nix-utils.output.lib.nuget.deps;
# Usage: export NETRC="$(agenix -d netrc.age)" in `./nix/secrets`
netrcConfig = builtins.getEnv "NETRC";
scripts = import ./scripts { inherit pkgs; };
packageSources = import ./nix/sources.nix;
nodeModules = pkgs.callPackage ./nix/node-modules.nix { };
client = pkgs.callPackage ./src/Client {
inherit
deps
dotnet-sdk
netrcConfig
nodeModules
packageSources
;
};
server = pkgs.callPackage ./src/Server {
inherit
deps
client
dotnet-sdk
dotnet-runtime
netrcConfig
packageSources
version
;
};
container = pkgs.dockerTools.buildLayeredImage {
name = "Fornix";
tag = version;
created = "now";
contents = [
server
pkgs.dockerTools.caCertificates
pkgs.busybox
pkgs.dockerTools.binSh
];
extraCommands = ''
mkdir -p app
cp -r ${server}/lib/Fornix/* app
'';
config = {
cmd = [ "Server" ];
workingDir = "/app";
};
};
in
{
inherit
client
server
container
;
checks = {
pre-commit = import ./nix/pre-commit.nix;
};
}

146
nix/default.nix Normal file
View File

@@ -0,0 +1,146 @@
/*
This file is provided under the MIT licence:
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the Software), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED AS IS, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
# Generated by npins. Do not modify; will be overwritten regularly
let
data = builtins.fromJSON (builtins.readFile ./sources.json);
version = data.version;
# https://github.com/NixOS/nixpkgs/blob/0258808f5744ca980b9a1f24fe0b1e6f0fecee9c/lib/lists.nix#L295
range =
first: last: if first > last then [ ] else builtins.genList (n: first + n) (last - first + 1);
# https://github.com/NixOS/nixpkgs/blob/0258808f5744ca980b9a1f24fe0b1e6f0fecee9c/lib/strings.nix#L257
stringToCharacters = s: map (p: builtins.substring p 1 s) (range 0 (builtins.stringLength s - 1));
# https://github.com/NixOS/nixpkgs/blob/0258808f5744ca980b9a1f24fe0b1e6f0fecee9c/lib/strings.nix#L269
stringAsChars = f: s: concatStrings (map f (stringToCharacters s));
concatMapStrings = f: list: concatStrings (map f list);
concatStrings = builtins.concatStringsSep "";
# If the environment variable NPINS_OVERRIDE_${name} is set, then use
# the path directly as opposed to the fetched source.
# (Taken from Niv for compatibility)
mayOverride =
name: path:
let
envVarName = "NPINS_OVERRIDE_${saneName}";
saneName = stringAsChars (c: if (builtins.match "[a-zA-Z0-9]" c) == null then "_" else c) name;
ersatz = builtins.getEnv envVarName;
in
if ersatz == "" then
path
else
# this turns the string into an actual Nix path (for both absolute and
# relative paths)
builtins.trace "Overriding path of \"${name}\" with \"${ersatz}\" due to set \"${envVarName}\"" (
if builtins.substring 0 1 ersatz == "/" then
/. + ersatz
else
/. + builtins.getEnv "PWD" + "/${ersatz}"
);
mkSource =
name: spec:
assert spec ? type;
let
path =
if spec.type == "Git" then
mkGitSource spec
else if spec.type == "GitRelease" then
mkGitSource spec
else if spec.type == "PyPi" then
mkPyPiSource spec
else if spec.type == "Channel" then
mkChannelSource spec
else if spec.type == "Tarball" then
mkTarballSource spec
else
builtins.throw "Unknown source type ${spec.type}";
in
spec // { outPath = mayOverride name path; };
mkGitSource =
{
repository,
revision,
url ? null,
submodules,
hash,
branch ? null,
...
}:
assert repository ? type;
# At the moment, either it is a plain git repository (which has an url), or it is a GitHub/GitLab repository
# In the latter case, there we will always be an url to the tarball
if url != null && !submodules then
builtins.fetchTarball {
inherit url;
sha256 = hash; # FIXME: check nix version & use SRI hashes
}
else
let
url =
if repository.type == "Git" then
repository.url
else if repository.type == "GitHub" then
"https://github.com/${repository.owner}/${repository.repo}.git"
else if repository.type == "GitLab" then
"${repository.server}/${repository.repo_path}.git"
else
throw "Unrecognized repository type ${repository.type}";
urlToName =
url: rev:
let
matched = builtins.match "^.*/([^/]*)(\\.git)?$" url;
short = builtins.substring 0 7 rev;
appendShort = if (builtins.match "[a-f0-9]*" rev) != null then "-${short}" else "";
in
"${if matched == null then "source" else builtins.head matched}${appendShort}";
name = urlToName url revision;
in
builtins.fetchGit {
rev = revision;
inherit name;
# hash = hash;
inherit url submodules;
};
mkPyPiSource =
{ url, hash, ... }:
builtins.fetchurl {
inherit url;
sha256 = hash;
};
mkChannelSource =
{ url, hash, ... }:
builtins.fetchTarball {
inherit url;
sha256 = hash;
};
mkTarballSource =
{
url,
locked_url ? url,
hash,
...
}:
builtins.fetchTarball {
url = locked_url;
sha256 = hash;
};
in
if version == 5 then
builtins.mapAttrs mkSource data.pins
else
throw "Unsupported format version ${toString version} in sources.json. Try running `npins upgrade`"

52
nix/node-modules.nix Normal file
View File

@@ -0,0 +1,52 @@
{
bun,
stdenvNoCC,
nix-gitignore,
writableTmpDirAsHomeHook,
}:
stdenvNoCC.mkDerivation {
name = "node-modules";
nativeBuildInputs = [
bun
writableTmpDirAsHomeHook
];
src = nix-gitignore.gitignoreSource [ ] ../.;
dontConfigure = true;
# Required else we get errors that our fixed-output derivation references store paths
dontFixup = true;
# Only install dependencies, don't build
buildPhase = ''
runHook preBuild
export BUN_INSTALL_CACHE_DIR=$(mktemp -d)
# Disable post-install scripts to avoid shebang issues
bun install \
--frozen-lockfile \
--ignore-scripts \
--backend copyfile \
--no-progress \
--force
runHook postBuild
'';
installPhase = ''
runHook preInstall
mkdir -p $out
cp -r node_modules $out/
runHook postInstall
'';
outputHashMode = "recursive";
outputHashAlgo = "sha256";
# NOTE: Empty this when a new dependency is added
outputHash = "sha256-U1SxIYa59qnoKOqqxWDXUEDhSO9W0yvffbRjEn72/lw=";
}

49
nix/sources.json Normal file
View File

@@ -0,0 +1,49 @@
{
"pins": {
"agenix": {
"type": "Git",
"repository": {
"type": "GitHub",
"owner": "ryantm",
"repo": "agenix"
},
"branch": "main",
"submodules": false,
"revision": "fcdea223397448d35d9b31f798479227e80183f6",
"url": "https://github.com/ryantm/agenix/archive/fcdea223397448d35d9b31f798479227e80183f6.tar.gz",
"hash": "1d4m7hsq727q7ndjqmgyl8vkbkqjwps962ygmv2mcc5dbqzgn963"
},
"nix-utils": {
"type": "Git",
"repository": {
"type": "Git",
"url": "https://git.sr.ht/~mrtz/nix-utils"
},
"branch": "trunk",
"submodules": false,
"revision": "098f594425d2b9dde0657becad0f6498d074f8b3",
"url": null,
"hash": "0hh52w1fkpr1xx6j8cjm6g88j2352yv2ysqm1q51j59y6f583vyb"
},
"nixpkgs": {
"type": "Channel",
"name": "nixpkgs-unstable",
"url": "https://releases.nixos.org/nixpkgs/nixpkgs-26.05pre905319.f720de590661/nixexprs.tar.xz",
"hash": "07n4hhch0j6n69b0zchdjg0l80z2xrdk7k57ykv90cvhklim5dz1"
},
"pre-commit": {
"type": "Git",
"repository": {
"type": "GitHub",
"owner": "cachix",
"repo": "git-hooks.nix"
},
"branch": "master",
"submodules": false,
"revision": "50b9238891e388c9fdc6a5c49e49c42533a1b5ce",
"url": "https://github.com/cachix/git-hooks.nix/archive/50b9238891e388c9fdc6a5c49e49c42533a1b5ce.tar.gz",
"hash": "01z1ihgpc7z7s97k9gn7vskw5zl8p6xavysdlmis1w0w4c3jfms2"
}
},
"version": 5
}

5
nix/sources.nix Normal file
View File

@@ -0,0 +1,5 @@
{
# "Fable.Lit" = "https://gitlab.com/api/v4/projects/61744837/packages/nuget/download";
# "Fable.Lit.Elmish" = "https://gitlab.com/api/v4/projects/61744837/packages/nuget/download";
# "Fable.Lit.React" = "https://gitlab.com/api/v4/projects/61744837/packages/nuget/download";
}

View File

@@ -3,14 +3,20 @@ let
port = 8000;
in
pkgs.mkShell {
nativeBuildInputs = [
packages = [
tilt
dapr-cli
# dotnetCorePackages.sdk_9_0
dotnetCorePackages.sdk_10_0
fable
dotnet-outdated
fantomas
fsautocomplete
tailwindcss_4
bun
];
DOTNET_ROOT = "${dotnet-sdk}/share/dotnet";
DOTNET_CLI_TELEMETRY_OPTOUT = "true";
DOCKER_BUILDKIT = 0;
LOG_LEVEL = 4;

View File

@@ -1,7 +1,7 @@
<?xml version="1.0" encoding="utf-8"?>
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>net9.0</TargetFramework>
<TargetFramework>net10.0</TargetFramework>
<DefineConstants>FABLE_COMPILER</DefineConstants>
<RestorePackagesWithLockFile>true</RestorePackagesWithLockFile>
</PropertyGroup>
@@ -23,6 +23,6 @@
<PackageReference Include="Fable.Remoting.Client" Version="7.35.0" />
<PackageReference Include="Elmish" Version="5.0.2" />
<PackageReference Include="Thoth.Json" Version="10.4.1" />
<PackageReference Update="FSharp.Core" Version="9.0.303" />
<PackageReference Update="FSharp.Core" Version="10.0.101" />
</ItemGroup>
</Project>

77
src/Client/default.nix Normal file
View File

@@ -0,0 +1,77 @@
{
bun,
lib,
deps,
pkgs,
fable,
nodejs,
tailwindcss_4,
dotnet-sdk,
netrcConfig,
nodeModules,
nix-gitignore,
packageSources,
buildDotnetModule,
}:
let
name = "Fornix.Client";
in
buildDotnetModule {
name = name;
inherit dotnet-sdk;
src = nix-gitignore.gitignoreSource [ ] ../..;
projectFile = "src/Client/Client.fsproj";
nugetDeps = deps {
inherit
pkgs
netrcConfig
packageSources
;
name = name;
lockfiles = [
./packages.lock.json
../Shared/packages.lock.json
];
};
# Skip the default dotnet build since we're using Fable
dontDotnetBuild = true;
dontFixup = true;
dontPatchELF = true;
dontStrip = true;
buildInput = [
nodejs
fable
bun
];
buildPhase = ''
runHook preBuild
cp -r ${nodeModules}/node_modules ./.
pushd src/Client
${lib.getExe tailwindcss_4} -i public/style.css -o dist/public/tailwindStyle.css
${lib.getExe fable} --verbose -e .jsx -o build
${lib.getExe bun} ../../node_modules/.bin/vite build -d --mode production
popd
mv src/Client/dist .
runHook postBuild
'';
installPhase = ''
runHook preInstall
mkdir -p $out
mv dist $out/public
runHook postInstall
'';
}

View File

@@ -1,7 +1,7 @@
{
"version": 1,
"dependencies": {
"net9.0": {
"net10.0": {
"Elmish": {
"type": "Direct",
"requested": "[5.0.2, )",
@@ -75,9 +75,9 @@
},
"FSharp.Core": {
"type": "Direct",
"requested": "[9.0.303, )",
"resolved": "9.0.303",
"contentHash": "6JlV8aD8qQvcmfoe/PMOxCHXc0uX4lR23u0fAyQtnVQxYULLoTZgwgZHSnRcuUHOvS3wULFWcwdnP1iwslH60g=="
"requested": "[10.0.101, )",
"resolved": "10.0.101",
"contentHash": "mrS3J7cLtvXM3u3CmiaFq8oyBdlevzZY1VAAAbFk1gUDQtDEjUOybN5XpQglx5wAgJ0wLdDl6OSSfS7ZDFNcpA=="
},
"FSharp.Data": {
"type": "Direct",
@@ -322,8 +322,7 @@
"resolved": "1.4.36",
"contentHash": "1xLk0SBF1nedD74B77rcArjD2d+DeZwbNI7BVCAyKwIBERo1VoX8Mf4AtX0OV2L3ZeM/XS1b6BuhXCyoh0KBnw==",
"dependencies": {
"FSharp.Core": "4.7.0",
"System.Text.Json": "6.0.10"
"FSharp.Core": "4.7.0"
}
},
"Newtonsoft.Json": {
@@ -331,25 +330,6 @@
"resolved": "13.0.1",
"contentHash": "ppPFpBcvxdsfUonNcvITKqLl3bqxWbDCZIzDWHzjpdAHRFfZe0Dw9HmA0+za13IdyrgJwpkDTDA9fHaxOrt20A=="
},
"System.IO.Pipelines": {
"type": "Transitive",
"resolved": "10.0.1",
"contentHash": "26LbFXHKd7PmRnWlkjnYgmjd5B6HYVG+1MpTO25BdxTJnx6D0O16JPAC/S4YBqjtt4YpfGj1QO/Ss6SPMGEGQw=="
},
"System.Text.Encodings.Web": {
"type": "Transitive",
"resolved": "10.0.1",
"contentHash": "cVAka0o1rJJ5/De0pjNs7jcaZk5hUGf1HGzUyVmE2MEB1Vf0h/8qsWxImk1zjitCbeD2Avaq2P2+usdvqgbeVQ=="
},
"System.Text.Json": {
"type": "Transitive",
"resolved": "10.0.1",
"contentHash": "EsgwDgU1PFqhrFA9l5n+RBu76wFhNGCEwu8ITrBNhjPP3MxLyklroU5GIF8o6JYpYg6T4KD/VICfMdgPAvNp5g==",
"dependencies": {
"System.IO.Pipelines": "10.0.1",
"System.Text.Encodings.Web": "10.0.1"
}
},
"Thoth.Json.Net": {
"type": "Transitive",
"resolved": "12.0.0",
@@ -363,12 +343,11 @@
"shared": {
"type": "Project",
"dependencies": {
"FSharp.Core": "[9.0.303, )",
"FSharp.Core": "[10.0.101, )",
"FSharp.Data": "[6.6.0, )",
"FSharp.SystemTextJson": "[1.4.36, )",
"Feliz": "[2.9.0, )",
"Feliz.ViewEngine": "[1.0.3, )",
"System.Text.Json": "[10.0.1, )",
"Thoth.Json.Net": "[12.0.0, )"
}
}

View File

@@ -2,7 +2,7 @@
<Project Sdk="Microsoft.NET.Sdk.Web">
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net9.0</TargetFramework>
<TargetFramework>net10.0</TargetFramework>
<RestorePackagesWithLockFile>true</RestorePackagesWithLockFile>
</PropertyGroup>
<ItemGroup>
@@ -38,6 +38,6 @@
<PackageReference Include="Serilog.Expressions" Version="5.0.0" />
<PackageReference Include="Thoth.Json.Giraffe" Version="6.0.0" />
<PackageReference Include="Thoth.Json.Net" Version="12.0.0" />
<PackageReference Update="FSharp.Core" Version="9.0.300" />
<PackageReference Update="FSharp.Core" Version="10.0.101" />
</ItemGroup>
</Project>

40
src/Server/default.nix Normal file
View File

@@ -0,0 +1,40 @@
{
deps,
pkgs,
client,
dotnet-sdk,
netrcConfig,
nix-gitignore,
dotnet-runtime,
packageSources,
buildDotnetModule,
version,
}:
let
name = "Fornix.Server";
in
buildDotnetModule {
pname = name;
inherit dotnet-sdk dotnet-runtime version;
src = nix-gitignore.gitignoreSource [ ] ../..;
projectFile = "src/Server/Server.fsproj";
dotnetRestoreFlags = "--force-evaluate";
nugetDeps = deps {
pkgs = pkgs;
name = name;
netrcConfig = netrcConfig;
packageSources = packageSources;
lockfiles = [
./packages.lock.json
../Shared/packages.lock.json
];
};
doCheck = false;
postInstall = ''
cp -r ${client}/public/* $out/lib/Fornix/public
'';
}

View File

@@ -1,7 +1,7 @@
{
"version": 1,
"dependencies": {
"net9.0": {
"net10.0": {
"Argu": {
"type": "Direct",
"requested": "[6.2.5, )",
@@ -53,16 +53,14 @@
"FSharp.Core": "6.0.0",
"Fable.Remoting.Json": "2.25.0",
"Fable.Remoting.MsgPack": "1.25.0",
"Microsoft.AspNetCore.WebUtilities": "2.3.0",
"Microsoft.IO.RecyclableMemoryStream": "[3.0.0, 4.0.0)",
"Microsoft.Net.Http.Headers": "2.3.0"
"Microsoft.IO.RecyclableMemoryStream": "[3.0.0, 4.0.0)"
}
},
"FSharp.Core": {
"type": "Direct",
"requested": "[9.0.300, )",
"resolved": "9.0.300",
"contentHash": "TVt2J7RCE1KCS2IaONF+p8/KIZ1eHNbW+7qmKF6hGoD4tXl+o07ja1mPtFjMqRa5uHMFaTrGTPn/m945WnDLiQ=="
"requested": "[10.0.101, )",
"resolved": "10.0.101",
"contentHash": "mrS3J7cLtvXM3u3CmiaFq8oyBdlevzZY1VAAAbFk1gUDQtDEjUOybN5XpQglx5wAgJ0wLdDl6OSSfS7ZDFNcpA=="
},
"FSharp.Data": {
"type": "Direct",
@@ -86,8 +84,7 @@
"resolved": "1.4.36",
"contentHash": "1xLk0SBF1nedD74B77rcArjD2d+DeZwbNI7BVCAyKwIBERo1VoX8Mf4AtX0OV2L3ZeM/XS1b6BuhXCyoh0KBnw==",
"dependencies": {
"FSharp.Core": "4.7.0",
"System.Text.Json": "6.0.10"
"FSharp.Core": "4.7.0"
}
},
"FSharpPlus": {
@@ -108,22 +105,14 @@
"FSharp.Core": "6.0.0",
"FSharp.SystemTextJson": "1.3.13",
"Giraffe.ViewEngine": "1.4.0",
"Microsoft.IO.RecyclableMemoryStream": "3.0.1",
"System.Text.Json": "8.0.6"
"Microsoft.IO.RecyclableMemoryStream": "3.0.1"
}
},
"Microsoft.AspNetCore.ResponseCaching": {
"type": "Direct",
"requested": "[2.3.0, )",
"resolved": "2.3.0",
"contentHash": "s8Hzzh+8wxYUgOZcmWFqwN6nW4kelBUrSpZ5a+nRw9zCi/DifhqIzpALyQk3+3U0vPJfCSY/uo5pSeHGv5CBYA==",
"dependencies": {
"Microsoft.AspNetCore.Http": "2.3.0",
"Microsoft.AspNetCore.Http.Extensions": "2.3.0",
"Microsoft.AspNetCore.ResponseCaching.Abstractions": "2.3.0",
"Microsoft.Extensions.Caching.Memory": "8.0.1",
"Microsoft.Extensions.Logging.Abstractions": "8.0.2"
}
"contentHash": "s8Hzzh+8wxYUgOZcmWFqwN6nW4kelBUrSpZ5a+nRw9zCi/DifhqIzpALyQk3+3U0vPJfCSY/uo5pSeHGv5CBYA=="
},
"Newtonsoft.Json": {
"type": "Direct",
@@ -420,213 +409,10 @@
"Microsoft.IdentityModel.Protocols.OpenIdConnect": "6.10.0"
}
},
"Microsoft.AspNetCore.Http": {
"type": "Transitive",
"resolved": "2.3.0",
"contentHash": "I9azEG2tZ4DDHAFgv+N38e6Yhttvf+QjE2j2UYyCACE7Swm5/0uoihCMWZ87oOZYeqiEFSxbsfpT71OYHe2tpw==",
"dependencies": {
"Microsoft.AspNetCore.Http.Abstractions": "2.3.0",
"Microsoft.AspNetCore.WebUtilities": "2.3.0",
"Microsoft.Extensions.ObjectPool": "8.0.11",
"Microsoft.Extensions.Options": "8.0.2",
"Microsoft.Net.Http.Headers": "2.3.0"
}
},
"Microsoft.AspNetCore.Http.Abstractions": {
"type": "Transitive",
"resolved": "2.3.0",
"contentHash": "39r9PPrjA6s0blyFv5qarckjNkaHRA5B+3b53ybuGGNTXEj1/DStQJ4NWjFL6QTRQpL9zt7nDyKxZdJOlcnq+Q==",
"dependencies": {
"Microsoft.AspNetCore.Http.Features": "2.3.0",
"System.Text.Encodings.Web": "8.0.0"
}
},
"Microsoft.AspNetCore.Http.Extensions": {
"type": "Transitive",
"resolved": "2.3.0",
"contentHash": "EY2u/wFF5jsYwGXXswfQWrSsFPmiXsniAlUWo3rv/MGYf99ZFsENDnZcQP6W3c/+xQmQXq0NauzQ7jyy+o1LDQ==",
"dependencies": {
"Microsoft.AspNetCore.Http.Abstractions": "2.3.0",
"Microsoft.Extensions.FileProviders.Abstractions": "8.0.0",
"Microsoft.Net.Http.Headers": "2.3.0",
"System.Buffers": "4.6.0"
}
},
"Microsoft.AspNetCore.Http.Features": {
"type": "Transitive",
"resolved": "2.3.0",
"contentHash": "f10WUgcsKqrkmnz6gt8HeZ7kyKjYN30PO7cSic1lPtH7paPtnQqXPOveul/SIPI43PhRD4trttg4ywnrEmmJpA==",
"dependencies": {
"Microsoft.Extensions.Primitives": "8.0.0"
}
},
"Microsoft.AspNetCore.ResponseCaching.Abstractions": {
"type": "Transitive",
"resolved": "2.3.0",
"contentHash": "VTqhxnUiawKS22fss5fr/NMJ4MVQHFUgqyWOIaJ9pUY+jmYGCAa+VYfB5DLJYmsD4AhdKnlO6I9lML5tUbDNNA==",
"dependencies": {
"Microsoft.Extensions.Primitives": "8.0.0"
}
},
"Microsoft.AspNetCore.WebUtilities": {
"type": "Transitive",
"resolved": "2.3.0",
"contentHash": "trbXdWzoAEUVd0PE2yTopkz4kjZaAIA7xUWekd5uBw+7xE8Do/YOVTeb9d9koPTlbtZT539aESJjSLSqD8eYrQ==",
"dependencies": {
"Microsoft.Net.Http.Headers": "2.3.0",
"System.Text.Encodings.Web": "8.0.0"
}
},
"Microsoft.CSharp": {
"type": "Transitive",
"resolved": "4.5.0",
"contentHash": "kaj6Wb4qoMuH3HySFJhxwQfe8R/sJsNJnANrvv8WdFPMoNbKY5htfNscv+LHCu5ipz+49m2e+WQXpLXr9XYemQ=="
},
"Microsoft.Extensions.Caching.Abstractions": {
"type": "Transitive",
"resolved": "8.0.0",
"contentHash": "3KuSxeHoNYdxVYfg2IRZCThcrlJ1XJqIXkAWikCsbm5C/bCjv7G0WoKDyuR98Q+T607QT2Zl5GsbGRkENcV2yQ==",
"dependencies": {
"Microsoft.Extensions.Primitives": "8.0.0"
}
},
"Microsoft.Extensions.Caching.Memory": {
"type": "Transitive",
"resolved": "8.0.1",
"contentHash": "HFDnhYLccngrzyGgHkjEDU5FMLn4MpOsr5ElgsBMC4yx6lJh4jeWO7fHS8+TXPq+dgxCmUa/Trl8svObmwW4QA==",
"dependencies": {
"Microsoft.Extensions.Caching.Abstractions": "8.0.0",
"Microsoft.Extensions.DependencyInjection.Abstractions": "8.0.2",
"Microsoft.Extensions.Logging.Abstractions": "8.0.2",
"Microsoft.Extensions.Options": "8.0.2",
"Microsoft.Extensions.Primitives": "8.0.0"
}
},
"Microsoft.Extensions.Configuration": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "H4SWETCh/cC5L1WtWchHR6LntGk3rDTTznZMssr4cL8IbDmMWBxY+MOGDc/ASnqNolLKPIWHWeuC1ddiL/iNPw==",
"dependencies": {
"Microsoft.Extensions.Configuration.Abstractions": "10.0.0",
"Microsoft.Extensions.Primitives": "10.0.0"
}
},
"Microsoft.Extensions.Configuration.Abstractions": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "d2kDKnCsJvY7mBVhcjPSp9BkJk48DsaHPg5u+Oy4f8XaOqnEedRy/USyvnpHL92wpJ6DrTPy7htppUUzskbCXQ==",
"dependencies": {
"Microsoft.Extensions.Primitives": "10.0.0"
}
},
"Microsoft.Extensions.Configuration.Binder": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "tMF9wNh+hlyYDWB8mrFCQHQmWHlRosol1b/N2Jrefy1bFLnuTlgSYmPyHNmz8xVQgs7DpXytBRWxGhG+mSTp0g==",
"dependencies": {
"Microsoft.Extensions.Configuration": "10.0.0",
"Microsoft.Extensions.Configuration.Abstractions": "10.0.0"
}
},
"Microsoft.Extensions.DependencyInjection": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "f0RBabswJq+gRu5a+hWIobrLWiUYPKMhCD9WO3sYBAdSy3FFH14LMvLVFZc2kPSCimBLxSuitUhsd6tb0TAY6A==",
"dependencies": {
"Microsoft.Extensions.DependencyInjection.Abstractions": "10.0.0"
}
},
"Microsoft.Extensions.DependencyInjection.Abstractions": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "L3AdmZ1WOK4XXT5YFPEwyt0ep6l8lGIPs7F5OOBZc77Zqeo01Of7XXICy47628sdVl0v/owxYJTe86DTgFwKCA=="
},
"Microsoft.Extensions.DependencyModel": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "RFYJR7APio/BiqdQunRq6DB+nDB6nc2qhHr77mlvZ0q0BT8PubMXN7XicmfzCbrDE/dzhBnUKBRXLTcqUiZDGg==",
"dependencies": {
"System.Text.Encodings.Web": "10.0.0",
"System.Text.Json": "10.0.0"
}
},
"Microsoft.Extensions.Diagnostics.Abstractions": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "SfK89ytD61S7DgzorFljSkUeluC1ncn6dtZgwc0ot39f/BEYWBl5jpgvodxduoYAs1d9HG8faCDRZxE95UMo2A==",
"dependencies": {
"Microsoft.Extensions.DependencyInjection.Abstractions": "10.0.0",
"Microsoft.Extensions.Options": "10.0.0",
"System.Diagnostics.DiagnosticSource": "10.0.0"
}
},
"Microsoft.Extensions.FileProviders.Abstractions": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "/ppSdehKk3fuXjlqCDgSOtjRK/pSHU8eWgzSHfHdwVm5BP4Dgejehkw+PtxKG2j98qTDEHDst2Y99aNsmJldmw==",
"dependencies": {
"Microsoft.Extensions.Primitives": "10.0.0"
}
},
"Microsoft.Extensions.Hosting.Abstractions": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "KrN6TGFwCwqOkLLk/idW/XtDQh+8In+CL9T4M1Dx+5ScsjTq4TlVbal8q532m82UYrMr6RiQJF2HvYCN0QwVsA==",
"dependencies": {
"Microsoft.Extensions.Configuration.Abstractions": "10.0.0",
"Microsoft.Extensions.DependencyInjection.Abstractions": "10.0.0",
"Microsoft.Extensions.Diagnostics.Abstractions": "10.0.0",
"Microsoft.Extensions.FileProviders.Abstractions": "10.0.0",
"Microsoft.Extensions.Logging.Abstractions": "10.0.0"
}
},
"Microsoft.Extensions.Http": {
"type": "Transitive",
"resolved": "3.1.0",
"contentHash": "DLigdcV0nYaT6/ly0rnfP80BnXq8NNd/h8/SkfY39uio7Bd9LauVntp6RcRh1Kj23N+uf80GgL7Win6P3BCtoQ==",
"dependencies": {
"Microsoft.Extensions.DependencyInjection.Abstractions": "3.1.0",
"Microsoft.Extensions.Logging": "3.1.0",
"Microsoft.Extensions.Options": "3.1.0"
}
},
"Microsoft.Extensions.Logging": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "BStFkd5CcnEtarlcgYDBcFzGYCuuNMzPs02wN3WBsOFoYIEmYoUdAiU+au6opzoqfTYJsMTW00AeqDdnXH2CvA==",
"dependencies": {
"Microsoft.Extensions.DependencyInjection": "10.0.0",
"Microsoft.Extensions.Logging.Abstractions": "10.0.0",
"Microsoft.Extensions.Options": "10.0.0"
}
},
"Microsoft.Extensions.Logging.Abstractions": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "FU/IfjDfwaMuKr414SSQNTIti/69bHEMb+QKrskRb26oVqpx3lNFXMjs/RC9ZUuhBhcwDM2BwOgoMw+PZ+beqQ==",
"dependencies": {
"Microsoft.Extensions.DependencyInjection.Abstractions": "10.0.0",
"System.Diagnostics.DiagnosticSource": "10.0.0"
}
},
"Microsoft.Extensions.ObjectPool": {
"type": "Transitive",
"resolved": "8.0.11",
"contentHash": "6ApKcHNJigXBfZa6XlDQ8feJpq7SG1ogZXg6M4FiNzgd6irs3LUAzo0Pfn4F2ZI9liGnH1XIBR/OtSbZmJAV5w=="
},
"Microsoft.Extensions.Options": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "8oCAgXOow5XDrY9HaXX1QmH3ORsyZO/ANVHBlhLyCeWTH5Sg4UuqZeOTWJi6484M+LqSx0RqQXDJtdYy2BNiLQ==",
"dependencies": {
"Microsoft.Extensions.DependencyInjection.Abstractions": "10.0.0",
"Microsoft.Extensions.Primitives": "10.0.0"
}
},
"Microsoft.Extensions.Primitives": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "inRnbpCS0nwO/RuoZIAqxQUuyjaknOOnCEZB55KSMMjRhl0RQDttSmLSGsUJN3RQ3ocf5NDLFd2mOQViHqMK5w=="
"contentHash": "RFYJR7APio/BiqdQunRq6DB+nDB6nc2qhHr77mlvZ0q0BT8PubMXN7XicmfzCbrDE/dzhBnUKBRXLTcqUiZDGg=="
},
"Microsoft.IdentityModel.JsonWebTokens": {
"type": "Transitive",
@@ -664,9 +450,7 @@
"resolved": "6.10.0",
"contentHash": "qbf1NslutDB4oLrriYTJpy7oB1pbh2ej2lEHd2IPDQH9C74ysOdhU5wAC7KoXblldbo7YsNR2QYFOqQM/b0Rsg==",
"dependencies": {
"Microsoft.CSharp": "4.5.0",
"Microsoft.IdentityModel.Logging": "6.10.0",
"System.Security.Cryptography.Cng": "4.5.0"
"Microsoft.IdentityModel.Logging": "6.10.0"
}
},
"Microsoft.IO.RecyclableMemoryStream": {
@@ -674,32 +458,16 @@
"resolved": "3.0.1",
"contentHash": "s/s20YTVY9r9TPfTrN5g8zPF1YhwxyqO6PxUkrYTGI2B+OGPe9AdajWZrLhFqXIvqIW23fnUE4+ztrUWNU1+9g=="
},
"Microsoft.Net.Http.Headers": {
"type": "Transitive",
"resolved": "2.3.0",
"contentHash": "/M0wVg6tJUOHutWD3BMOUVZAioJVXe0tCpFiovzv0T9T12TBf4MnaHP0efO8TCr1a6O9RZgQeZ9Gdark8L9XdA==",
"dependencies": {
"Microsoft.Extensions.Primitives": "8.0.0",
"System.Buffers": "4.6.0"
}
},
"prometheus-net": {
"type": "Transitive",
"resolved": "8.2.1",
"contentHash": "3wVgdEPOCBF752s2xps5T+VH+c9mJK8S8GKEDg49084P6JZMumTZI5Te6aJ9MQpX0sx7om6JOnBpIi7ZBmmiDQ==",
"dependencies": {
"Microsoft.Extensions.Http": "3.1.0",
"Microsoft.Extensions.ObjectPool": "7.0.0"
}
"contentHash": "3wVgdEPOCBF752s2xps5T+VH+c9mJK8S8GKEDg49084P6JZMumTZI5Te6aJ9MQpX0sx7om6JOnBpIi7ZBmmiDQ=="
},
"Serilog.Extensions.Hosting": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "E7juuIc+gzoGxgzFooFgAV8g9BfiSXNKsUok9NmEpyAXg2odkcPsMa/Yo4axkJRlh0se7mkYQ1GXDaBemR+b6w==",
"dependencies": {
"Microsoft.Extensions.DependencyInjection.Abstractions": "10.0.0",
"Microsoft.Extensions.Hosting.Abstractions": "10.0.0",
"Microsoft.Extensions.Logging.Abstractions": "10.0.0",
"Serilog": "4.3.0",
"Serilog.Extensions.Logging": "10.0.0"
}
@@ -709,7 +477,6 @@
"resolved": "10.0.0",
"contentHash": "vx0kABKl2dWbBhhqAfTOk53/i8aV/5VaT3a6il9gn72Wqs2pM7EK2OB6No6xdqK2IaY6Zf9gdjLuK9BVa2rT+Q==",
"dependencies": {
"Microsoft.Extensions.Logging": "10.0.0",
"Serilog": "4.2.0"
}
},
@@ -726,7 +493,6 @@
"resolved": "10.0.0",
"contentHash": "LNq+ibS1sbhTqPV1FIE69/9AJJbfaOhnaqkzcjFy95o+4U+STsta9mi97f1smgXsWYKICDeGUf8xUGzd/52/uA==",
"dependencies": {
"Microsoft.Extensions.Configuration.Binder": "10.0.0",
"Microsoft.Extensions.DependencyModel": "10.0.0",
"Serilog": "4.3.0"
}
@@ -755,11 +521,6 @@
"Serilog": "4.2.0"
}
},
"System.Buffers": {
"type": "Transitive",
"resolved": "4.6.0",
"contentHash": "lN6tZi7Q46zFzAbRYXTIvfXcyvQQgxnY7Xm6C6xQ9784dEL1amjM6S6Iw4ZpsvesAKnRVsM4scrDQaDqSClkjA=="
},
"System.Configuration.ConfigurationManager": {
"type": "Transitive",
"resolved": "4.4.0",
@@ -768,11 +529,6 @@
"System.Security.Cryptography.ProtectedData": "4.4.0"
}
},
"System.Diagnostics.DiagnosticSource": {
"type": "Transitive",
"resolved": "10.0.0",
"contentHash": "0KdBK+h7G13PuOSC2R/DalAoFMvdYMznvGRuICtkdcUMXgl/gYXsG6z4yUvTxHSMACorWgHCU1Faq0KUHU6yAQ=="
},
"System.IdentityModel.Tokens.Jwt": {
"type": "Transitive",
"resolved": "6.10.0",
@@ -782,44 +538,19 @@
"Microsoft.IdentityModel.Tokens": "6.10.0"
}
},
"System.IO.Pipelines": {
"type": "Transitive",
"resolved": "10.0.1",
"contentHash": "26LbFXHKd7PmRnWlkjnYgmjd5B6HYVG+1MpTO25BdxTJnx6D0O16JPAC/S4YBqjtt4YpfGj1QO/Ss6SPMGEGQw=="
},
"System.Security.Cryptography.Cng": {
"type": "Transitive",
"resolved": "4.5.0",
"contentHash": "WG3r7EyjUe9CMPFSs6bty5doUqT+q9pbI80hlNzo2SkPkZ4VTuZkGWjpp77JB8+uaL4DFPRdBsAY+DX3dBK92A=="
},
"System.Security.Cryptography.ProtectedData": {
"type": "Transitive",
"resolved": "4.4.0",
"contentHash": "cJV7ScGW7EhatRsjehfvvYVBvtiSMKgN8bOVI0bQhnF5bU7vnHVIsH49Kva7i7GWaWYvmEzkYVk1TC+gZYBEog=="
},
"System.Text.Encodings.Web": {
"type": "Transitive",
"resolved": "10.0.1",
"contentHash": "cVAka0o1rJJ5/De0pjNs7jcaZk5hUGf1HGzUyVmE2MEB1Vf0h/8qsWxImk1zjitCbeD2Avaq2P2+usdvqgbeVQ=="
},
"System.Text.Json": {
"type": "Transitive",
"resolved": "10.0.1",
"contentHash": "EsgwDgU1PFqhrFA9l5n+RBu76wFhNGCEwu8ITrBNhjPP3MxLyklroU5GIF8o6JYpYg6T4KD/VICfMdgPAvNp5g==",
"dependencies": {
"System.IO.Pipelines": "10.0.1",
"System.Text.Encodings.Web": "10.0.1"
}
},
"shared": {
"type": "Project",
"dependencies": {
"FSharp.Core": "[9.0.303, )",
"FSharp.Core": "[10.0.100, )",
"FSharp.Data": "[6.6.0, )",
"FSharp.SystemTextJson": "[1.4.36, )",
"Feliz": "[2.9.0, )",
"Feliz.ViewEngine": "[1.0.3, )",
"System.Text.Json": "[10.0.1, )",
"Thoth.Json.Net": "[12.0.0, )"
}
}

View File

@@ -2,7 +2,8 @@
<PropertyGroup>
<OutputType>Lib</OutputType>
<TargetFramework>netstandard2.0</TargetFramework>
<TargetFramework>net10.0</TargetFramework>
<RestorePackagesWithLockFile>true</RestorePackagesWithLockFile>
</PropertyGroup>
<ItemGroup>
@@ -12,6 +13,7 @@
<PackageReference Include="Feliz.ViewEngine" Version="1.0.3" />
<PackageReference Include="System.Text.Json" Version="10.0.1" />
<PackageReference Include="Thoth.Json.Net" Version="12.0.0" />
<PackageReference Update="FSharp.Core" Version="10.0.101" />
</ItemGroup>
<ItemGroup>

View File

@@ -0,0 +1,239 @@
{
"version": 1,
"dependencies": {
"net10.0": {
"Feliz": {
"type": "Direct",
"requested": "[2.9.0, )",
"resolved": "2.9.0",
"contentHash": "8nyGREGA60RysdSBamVWmr68MG+3lLy76W17fBiGaKi7uMFbtRcYBLyNtp2NyGZFfnuWCEyDAmAXM5YFnDhbhg==",
"dependencies": {
"FSharp.Core": "4.7.2",
"Fable.ReactDom.Types": "18.2.0",
"Feliz.CompilerPlugins": "2.2.0"
}
},
"Feliz.ViewEngine": {
"type": "Direct",
"requested": "[1.0.3, )",
"resolved": "1.0.3",
"contentHash": "962ikmdW9oKmB4p6BJLM75D5SQJHFB+DmIUeKmHwoP1uZaXbvsXbQKQFi5slzGGUvOP8L3TYhRex6QVJri0Zjw==",
"dependencies": {
"Fsharp.Core": "4.7.0"
}
},
"FSharp.Core": {
"type": "Direct",
"requested": "[10.0.101, )",
"resolved": "10.0.101",
"contentHash": "mrS3J7cLtvXM3u3CmiaFq8oyBdlevzZY1VAAAbFk1gUDQtDEjUOybN5XpQglx5wAgJ0wLdDl6OSSfS7ZDFNcpA=="
},
"FSharp.Data": {
"type": "Direct",
"requested": "[6.6.0, )",
"resolved": "6.6.0",
"contentHash": "AC87/VZV1iGrnK1uG6QhX22HZARlFiCqdlckzPDgdE3+fzc0ZNRR3Y4ny5vbLvfDj2rjFoJdmRZy6kzI1C/sQQ==",
"dependencies": {
"FSharp.Core": "6.0.1",
"FSharp.Data.Csv.Core": "6.6.0",
"FSharp.Data.Html.Core": "6.6.0",
"FSharp.Data.Http": "6.6.0",
"FSharp.Data.Json.Core": "6.6.0",
"FSharp.Data.Runtime.Utilities": "6.6.0",
"FSharp.Data.WorldBank.Core": "6.6.0",
"FSharp.Data.Xml.Core": "6.6.0"
}
},
"FSharp.SystemTextJson": {
"type": "Direct",
"requested": "[1.4.36, )",
"resolved": "1.4.36",
"contentHash": "1xLk0SBF1nedD74B77rcArjD2d+DeZwbNI7BVCAyKwIBERo1VoX8Mf4AtX0OV2L3ZeM/XS1b6BuhXCyoh0KBnw==",
"dependencies": {
"FSharp.Core": "4.7.0"
}
},
"System.Text.Json": {
"type": "Direct",
"requested": "[10.0.1, )",
"resolved": "10.0.1",
"contentHash": "EsgwDgU1PFqhrFA9l5n+RBu76wFhNGCEwu8ITrBNhjPP3MxLyklroU5GIF8o6JYpYg6T4KD/VICfMdgPAvNp5g=="
},
"Thoth.Json.Net": {
"type": "Direct",
"requested": "[12.0.0, )",
"resolved": "12.0.0",
"contentHash": "n2YyONYdWCFS4Pu7wrqgV/l5tPuN+t3gxEfs/2RwqCiQkRnbgKs9dK61zHeZS5YganAoFbxLSwbaNL7SvSrS9g==",
"dependencies": {
"FSharp.Core": "4.7.2",
"Fable.Core": "3.1.6",
"Newtonsoft.Json": "13.0.1"
}
},
"Fable.AST": {
"type": "Transitive",
"resolved": "4.2.1",
"contentHash": "/4V6U7Qw/WIRRxm9NJ7b+YTXTRCTk6/YKeJnbKYaVbtT45MstA3jkFvRfV0FqVFtkG9AL4uccetreygTjK7nbQ=="
},
"Fable.Browser.Blob": {
"type": "Transitive",
"resolved": "1.1.4",
"contentHash": "+6aq2ClPFbh/wFEtKuuIPwoZwi2GlUJ6RRykT0R+i95ZmK22nfE6iWpP+jfKxDnGgrm2AGC+btobAHWXbkC1Sw==",
"dependencies": {
"FSharp.Core": "4.7.2",
"Fable.Core": "3.0.0"
}
},
"Fable.Browser.Dom": {
"type": "Transitive",
"resolved": "2.4.4",
"contentHash": "wFGefU1Idqkwa6kKdvz5oyHL5yP+i+cvTHPeJGlF22fnqOozFurFIuPqGToqpgl9DfyWr7MyNvTiLFOkfXNqnA==",
"dependencies": {
"FSharp.Core": "4.7.2",
"Fable.Browser.Blob": "1.1.4",
"Fable.Browser.Event": "1.4.4",
"Fable.Browser.WebStorage": "1.0.4",
"Fable.Core": "3.0.0"
}
},
"Fable.Browser.Event": {
"type": "Transitive",
"resolved": "1.4.4",
"contentHash": "jGwS4fjwUNBXgGuu+mklDp9sx4ql0E6Ml5F/CI+8gxwgmxG4IdBTo3yIgF8m0doy7Tc9fgBhOfP3xdGMDgJBBQ==",
"dependencies": {
"FSharp.Core": "4.7.2",
"Fable.Browser.Gamepad": "1.0.3",
"Fable.Core": "3.0.0"
}
},
"Fable.Browser.Gamepad": {
"type": "Transitive",
"resolved": "1.0.3",
"contentHash": "3mIdAR8uy7eQoL+Nyp72OVWnIbTegoFD6yCvnqaHeWE2MZ3+Lc9EPMKDiHjX3VbImd1uQI57zg+hQJ6MTekgEA==",
"dependencies": {
"FSharp.Core": "4.7.2",
"Fable.Core": "3.0.0"
}
},
"Fable.Browser.WebStorage": {
"type": "Transitive",
"resolved": "1.0.4",
"contentHash": "kxKI1nM4TWIRjp4X0QfdbgdU3p1ite5E/to3/RqotnV5BTmS9Wl+yX38L0S4CTbnU+I6v8aPLYlZ/BKmtxggXQ==",
"dependencies": {
"FSharp.Core": "4.7.2",
"Fable.Browser.Event": "1.4.4",
"Fable.Core": "3.0.0"
}
},
"Fable.Core": {
"type": "Transitive",
"resolved": "3.2.7",
"contentHash": "XYvisWEqzYap+9USQGRyI4F9DmZY5EE3STMiwnvlSrwoqHmZRPHyQR3Rp2oGv/mpzNy7PViKdgCiKC/eviG2Ng==",
"dependencies": {
"FSharp.Core": "4.7.2"
}
},
"Fable.React.Types": {
"type": "Transitive",
"resolved": "18.3.0",
"contentHash": "/b8WZ3Bdfhqy9r60ZK9JGZaGNjIMb0ogsrvWIg3k7KfCEvJs5X6+7hCybVkyjVoxwzn9wLyYGRbh5wmuHQT/Vg==",
"dependencies": {
"FSharp.Core": "4.7.2",
"Fable.Browser.Dom": "2.4.4",
"Fable.Core": "3.2.7"
}
},
"Fable.ReactDom.Types": {
"type": "Transitive",
"resolved": "18.2.0",
"contentHash": "2WoBjsLiSgrvR68OJXko0iVaqeMbkPM5Bx813A1WlxOSCJ50M9fwnlwG/MUEZtiOIhQmku/YTJY5a8E8r1+j2Q==",
"dependencies": {
"FSharp.Core": "4.7.2",
"Fable.React.Types": "18.3.0"
}
},
"Feliz.CompilerPlugins": {
"type": "Transitive",
"resolved": "2.2.0",
"contentHash": "ACkO++Hp4lUrEx/axeehIL5/3R8jMnak+CYpzd0/kLpejp9BETtrgjHK7oj6Lh3V9fB7WoAKsCxyPSrm4ADN2w==",
"dependencies": {
"FSharp.Core": "4.7.2",
"Fable.AST": "4.2.1"
}
},
"FSharp.Data.Csv.Core": {
"type": "Transitive",
"resolved": "6.6.0",
"contentHash": "gbmHT+XraE1OjUyf/+bmIaluoMMj/34MC5IX0QNWr+K8fu+UjKg854p+fkG5JkzWej0+46CTV7hW/CWP425naA==",
"dependencies": {
"FSharp.Core": "6.0.1",
"FSharp.Data.Runtime.Utilities": "6.6.0"
}
},
"FSharp.Data.Html.Core": {
"type": "Transitive",
"resolved": "6.6.0",
"contentHash": "YxImykk5fUxw+rwvD26JfZYn/OAUataebsUobXu8KzkLtl/5fOhiPqpI54jAT4ysv2wHD5coCp30+5UsQXqxBQ==",
"dependencies": {
"FSharp.Core": "6.0.1",
"FSharp.Data.Csv.Core": "6.6.0",
"FSharp.Data.Runtime.Utilities": "6.6.0"
}
},
"FSharp.Data.Http": {
"type": "Transitive",
"resolved": "6.6.0",
"contentHash": "7nFDLYPqEps/F3Ay65Xm3YvS3OmARYB24xYv1CszOqurTZ76wM9vnsvyeFOMcCKXA+QgwK+eCa8cgyavmR1YxA==",
"dependencies": {
"FSharp.Core": "6.0.1"
}
},
"FSharp.Data.Json.Core": {
"type": "Transitive",
"resolved": "6.6.0",
"contentHash": "VhLkZwyzeMWsJHivY4GjLqIWh+gIm0rWW0BBlAh1M7XzmmumbPLDehUqOh6Nkm1R+N8iBhFgj7HBq6bmQzGnZA==",
"dependencies": {
"FSharp.Core": "6.0.1",
"FSharp.Data.Http": "6.6.0",
"FSharp.Data.Runtime.Utilities": "6.6.0"
}
},
"FSharp.Data.Runtime.Utilities": {
"type": "Transitive",
"resolved": "6.6.0",
"contentHash": "iLkCY0mQGxuIE2sEIFFOov9ZmWPwlQ0Jq51Xgqv+e0hbAPf2p4OaGp/DR4ye6VQCyVzHVCp9XyJQeHOhoWCQvA==",
"dependencies": {
"FSharp.Core": "6.0.1",
"FSharp.Data.Http": "6.6.0"
}
},
"FSharp.Data.WorldBank.Core": {
"type": "Transitive",
"resolved": "6.6.0",
"contentHash": "Tg6Hk0+61McNviq+zATBhIDoyslV07hZjYsrzz6IHagbze+1JNiz8FCpwsHh0uAzkdNUZK2/qsrHtMQvM0lpdg==",
"dependencies": {
"FSharp.Core": "6.0.1",
"FSharp.Data.Http": "6.6.0",
"FSharp.Data.Json.Core": "6.6.0",
"FSharp.Data.Runtime.Utilities": "6.6.0"
}
},
"FSharp.Data.Xml.Core": {
"type": "Transitive",
"resolved": "6.6.0",
"contentHash": "Z7U4mO0FHT5uHOYRLSK67izqJrCSvWpjcDPRQkJmYB5ge0sRfHWoKV8b4ttHLmpEg/eAdu64u00nITxpbZm+CA==",
"dependencies": {
"FSharp.Core": "6.0.1",
"FSharp.Data.Http": "6.6.0",
"FSharp.Data.Json.Core": "6.6.0",
"FSharp.Data.Runtime.Utilities": "6.6.0"
}
},
"Newtonsoft.Json": {
"type": "Transitive",
"resolved": "13.0.1",
"contentHash": "ppPFpBcvxdsfUonNcvITKqLl3bqxWbDCZIzDWHzjpdAHRFfZe0Dw9HmA0+za13IdyrgJwpkDTDA9fHaxOrt20A=="
}
}
}
}