From 6b13f04da94f2f604241c8382e13b6f483a69da4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=C3=A7ois=20Laurent?= <francois.laurent@posteo.net> Date: Fri, 21 Feb 2025 17:51:32 +0100 Subject: [PATCH 1/8] fix: tryopenfile updates :input on missing or failing input file --- src/files.jl | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/files.jl b/src/files.jl index 100d81d..a9f9a12 100644 --- a/src/files.jl +++ b/src/files.jl @@ -104,9 +104,15 @@ function tryopenfile(controller, path; reload::Bool=false) turn_load_animation_on(controller) end # + if !isfile(path) + @error "Cannot find file" file=path + hub[:input][] = nothing + return + end records = loadfile(path) if isempty(records) @info "Cannot load file" file=path + hub[:input][] = nothing return elseif haskey(hub, :input) hub[:input][] = path -- GitLab From 09e0467fd3e63d890df6d2f2dff9de80be67c876 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=C3=A7ois=20Laurent?= <francois.laurent@posteo.net> Date: Fri, 28 Mar 2025 17:44:06 +0100 Subject: [PATCH 2/8] feat: REST api (wip) --- Manifest.toml | 23 +++-- Project.toml | 3 + README.md | 13 --- src/LarvaTagger.jl | 2 + src/REST/Client.jl | 225 ++++++++++++++++++++++++++++++++++++++++++++ src/REST/Model.jl | 224 +++++++++++++++++++++++++++++++++++++++++++ src/REST/REST.jl | 8 ++ src/REST/Server.jl | 130 +++++++++++++++++++++++++ src/Taggers.jl | 83 ++++++++++++++-- src/backends.jl | 69 +++++++++----- src/cli_open.jl | 2 +- src/editor.jl | 5 + src/larvatagger.css | 3 +- src/wgl.jl | 26 +++-- test/rest_client.sh | 32 +++++++ test/rest_server.sh | 177 ++++++++++++++++++++++++++++++++++ 16 files changed, 962 insertions(+), 63 deletions(-) create mode 100644 src/REST/Client.jl create mode 100644 src/REST/Model.jl create mode 100644 src/REST/REST.jl create mode 100644 src/REST/Server.jl create mode 100755 test/rest_client.sh create mode 100755 test/rest_server.sh diff --git a/Manifest.toml b/Manifest.toml index cf255d7..af56fc6 100644 --- a/Manifest.toml +++ b/Manifest.toml @@ -1,8 +1,8 @@ # This file is machine-generated - editing it directly is not advised -julia_version = "1.10.8" +julia_version = "1.10.9" manifest_format = "2.0" -project_hash = "029a32b6e21d0f2c52e6dccd0a009e9681bdff18" +project_hash = "51a3effe31474c33a1cea491c41e13148b8635d0" [[deps.AbstractFFTs]] deps = ["LinearAlgebra"] @@ -503,10 +503,10 @@ uuid = "0234f1f7-429e-5d53-9886-15a909be8d59" version = "1.14.2+1" [[deps.HTTP]] -deps = ["Base64", "CodecZlib", "ConcurrentUtilities", "Dates", "ExceptionUnwrapping", "Logging", "LoggingExtras", "MbedTLS", "NetworkOptions", "OpenSSL", "Random", "SimpleBufferStream", "Sockets", "URIs", "UUIDs"] -git-tree-sha1 = "1336e07ba2eb75614c99496501a8f4b233e9fafe" +deps = ["Base64", "CodecZlib", "ConcurrentUtilities", "Dates", "ExceptionUnwrapping", "Logging", "LoggingExtras", "MbedTLS", "NetworkOptions", "OpenSSL", "PrecompileTools", "Random", "SimpleBufferStream", "Sockets", "URIs", "UUIDs"] +git-tree-sha1 = "c67b33b085f6e2faf8bf79a61962e7339a81129c" uuid = "cd3eb016-35fb-5094-929b-558a96fad6f3" -version = "1.10.10" +version = "1.10.15" [[deps.HarfBuzz_jll]] deps = ["Artifacts", "Cairo_jll", "Fontconfig_jll", "FreeType2_jll", "Glib_jll", "Graphite2_jll", "JLLWrappers", "Libdl", "Libffi_jll"] @@ -848,6 +848,11 @@ git-tree-sha1 = "1d2dd9b186742b0f317f2530ddcbf00eebb18e96" uuid = "23992714-dd62-5051-b70f-ba57cb901cac" version = "0.10.7" +[[deps.MIMEs]] +git-tree-sha1 = "1833212fd6f580c20d4291da9c1b4e8a655b128e" +uuid = "6c6e2e6c-3030-632d-7369-2d6c69616d65" +version = "1.0.0" + [[deps.MKL_jll]] deps = ["Artifacts", "IntelOpenMP_jll", "JLLWrappers", "LazyArtifacts", "Libdl", "oneTBB_jll"] git-tree-sha1 = "f046ccd0c6db2832a9f639e2c669c6fe867e5f4f" @@ -1025,7 +1030,7 @@ version = "3.2.4+0" [[deps.OpenLibm_jll]] deps = ["Artifacts", "Libdl"] uuid = "05823500-19ac-5b8b-9628-191a04bc5112" -version = "0.8.1+2" +version = "0.8.1+4" [[deps.OpenMPI_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "Hwloc_jll", "JLLWrappers", "LazyArtifacts", "Libdl", "MPIPreferences", "TOML", "Zlib_jll"] @@ -1062,6 +1067,12 @@ git-tree-sha1 = "dfdf5519f235516220579f949664f1bf44e741c5" uuid = "bac558e1-5e72-5ebc-8fee-abe8a469f55d" version = "1.6.3" +[[deps.Oxygen]] +deps = ["DataStructures", "Dates", "HTTP", "JSON3", "MIMEs", "Reexport", "RelocatableFolders", "Requires", "Sockets", "Statistics", "StructTypes"] +git-tree-sha1 = "2ad010b0de6172faf1d09ed5e0837eb0b7355bd8" +uuid = "df9a0d86-3283-4920-82dc-4555fc0d1d8b" +version = "1.5.16" + [[deps.PCRE2_jll]] deps = ["Artifacts", "Libdl"] uuid = "efcefdf7-47ab-520b-bdef-62a2eaa19f15" diff --git a/Project.toml b/Project.toml index 60848ef..4707dab 100644 --- a/Project.toml +++ b/Project.toml @@ -9,6 +9,8 @@ Colors = "5ae59095-9a9b-59fe-a467-6f913c188581" Dates = "ade2ca70-3891-5945-98fb-dc099432e06a" DocOpt = "968ba79b-81e4-546f-ab3a-2eecfa62a9db" Format = "1fa38f19-a742-5d3f-a2b9-30dd87b9d5f8" +HTTP = "cd3eb016-35fb-5094-929b-558a96fad6f3" +JSON3 = "0f8b85d8-7281-11e9-16c2-39a750bddbf1" LinearAlgebra = "37e2e46d-f89d-539d-b4ee-838fcccc9c8e" Logging = "56ddb016-857b-54e1-b83d-db4d58db5568" Makie = "ee78f7c6-11fb-53f2-987a-cfe4a2b5a57a" @@ -18,6 +20,7 @@ NyxWidgets = "c288fd06-43d3-4b04-8307-797133353e2e" Observables = "510215fc-4207-5dde-b226-833fc4488ee2" ObservationPolicies = "6317928a-6b1a-42e8-b853-b8e2fc3e9ca3" OrderedCollections = "bac558e1-5e72-5ebc-8fee-abe8a469f55d" +Oxygen = "df9a0d86-3283-4920-82dc-4555fc0d1d8b" PlanarLarvae = "c2615984-ef14-4d40-b148-916c85b43307" Random = "9a3f8284-a2c9-5f02-9a11-845980a1fd5c" StaticArrays = "90137ffa-7385-5640-81b9-e52037218182" diff --git a/README.md b/README.md index 1b9a1b2..9996377 100644 --- a/README.md +++ b/README.md @@ -213,19 +213,6 @@ The `--browser` argument may open a new tab in your web browser, but this featur The first time the application is loaded, it may take a while for a window in your web browser to open, and the data to be plotted. -### From the *Julia* interpreter - -As an alternative to the *larvatagger* script or command, in the *LarvaTagger* directory created above, launch the *Julia* interpreter: -``` -julia --project=. -``` -In the interpreter, to launch the editor, type: -``` -julia> using LarvaTagger; display(larvaeditor("path/to/data/file")) -``` - -To exit the interpreter, type `exit()` or press Ctrl+D. - ### macOS On some computers (typically macOS computers), the 2D larva view may show up twice as small as expected. diff --git a/src/LarvaTagger.jl b/src/LarvaTagger.jl index 00d344c..5c96f8e 100644 --- a/src/LarvaTagger.jl +++ b/src/LarvaTagger.jl @@ -32,6 +32,8 @@ include("players.jl") include("controllers.jl") include("Taggers.jl") using .Taggers +include("REST/REST.jl") +using .REST include("files.jl") include("backends.jl") include("cli_base.jl") diff --git a/src/REST/Client.jl b/src/REST/Client.jl new file mode 100644 index 0000000..61814f4 --- /dev/null +++ b/src/REST/Client.jl @@ -0,0 +1,225 @@ +module Client + +using PlanarLarvae.Datasets +import ..Taggers: Taggers, Tagger +import HTTP: HTTP +using JSON3 +using OrderedCollections: OrderedDict +using Observables + +export RemoteTagger, LTBackend, connect, listmodels, active_model_instance + +mutable struct RemoteTagger + endpoint::AbstractString + token::AbstractString # empty if not connected + backend::AbstractString + model_instance::AbstractString + output_filenames::Dict{String, String} # renaming rules +end + +function RemoteTagger(endpoint, backend, model_instance) + RemoteTagger(endpoint, "", backend, model_instance, Dict{String, String}()) +end + +connected(tagger) = !isempty(tagger.token) + +function connect!(tagger) + tagger.token = gettoken(tagger) + return tagger +end + +function gettoken(tagger) + if isempty(tagger.token) + resp = HTTP.get("$(tagger.endpoint)/get-token/$(tagger.backend)/$(tagger.model_instance)") + transcode(String, resp.body) + else + tagger.token + end +end + +function url(tagger::RemoteTagger, switch) + token = tagger.token + @assert !isnothing(token) + return "$(tagger.endpoint)/$switch/$(tagger.backend)/$(tagger.model_instance)/$token" +end + +function Base.close(tagger::RemoteTagger) + HTTP.get(url(tagger, "close")) + tagger.token = "" +end + +function listfiles(tagger::RemoteTagger, srcdir::String) + resp = HTTP.get("$(url(tagger, "list-files"))/$srcdir") + @info "listfiles" transcode(String, resp.body) + String[] +end + +function Taggers.pull(tagger::RemoteTagger, destdir::String) + cmd = url(tagger, "pull-file") + # destdir can be empty on macOS + destdir = isempty(destdir) ? pwd() : realpath(destdir) # strip end slash + destfiles = String[] + for filename in listfiles(tagger, "processed") + resp = HTTP.get("$cmd/$filename") + destfile = joinpath(destdir, filename) + open(destfile, "w") do f + write(f, resp.body) + end + push!(destfiles, destfile) + end + return destfiles +end + +function Taggers.resetdata(tagger::RemoteTagger, dir=nothing) + query = url(tagger, "reset-data") + if !isnothing(dir) + query = "$query/$dir" + end + HTTP.get(query) +end + +function Taggers.pushfile(tagger::RemoteTagger, src, dst) + @assert dst == basename(src) + Taggers.pushfile(tagger, src) +end + +function Taggers.pushfile(tagger::RemoteTagger, src) + request = url(tagger, "push-file") + @info "dummy push-file" src +end + +function Taggers.push(tagger::RemoteTagger, file::String, metadata; clean=true) + clean ? Taggers.resetdata(tagger) : Taggers.resetdata(tagger, "raw") + Taggers.push(tagger, file) + if !isnothing(metadata) + mktempdir() do dir + metadatafile = joinpath(dir, "metadata") + Datasets.to_json_file(metadatafile, metadata) + Taggers.pushfile(tagger, metadatafile) + end + end +end + +Taggers.run(tagger::RemoteTagger, switch) = HTTP.get(url(tagger, switch); retry=false) + +Taggers.predict(tagger::RemoteTagger) = Taggers.run(tagger, "predict") + +Taggers.embed(tagger::RemoteTagger) = Taggers.run(tagger, "embed") + + +struct LTBackend + endpoint + metadata + taggers + active_tagging_backend + active_tagger +end + +function LTBackend(endpoint) + metadata = Dict{String, OrderedDict{Symbol, Union{String, Dict{String, OrderedDict{Symbol, String}}}}}() + taggers = OrderedDict{String, OrderedDict{String, RemoteTagger}}() + active_tagging_backend = Observable{Union{Nothing, String}}(nothing) + active_tagger = Observable{Union{Nothing, RemoteTagger}}(nothing) + on(active_tagging_backend) do tagging_backend + if isnothing(tagging_backend) + active_tagger[] = nothing + elseif isnothing(active_tagger[]) || active_tagger[].backend != tagging_backend + active_tagger[] = first(values(taggers[tagging_backend])) + else + notify(active_tagger) + end + end + on(active_tagger) do tagger + if !isnothing(tagger) + @info "Tagger selected" backend=tagger.backend instance=tagger.model_instance + if tagger.backend != active_tagging_backend[] + active_tagging_backend[] = tagger.backend + end + end + end + LTBackend(endpoint, metadata, taggers, active_tagging_backend, active_tagger) +end + +function active_model_instance(back::LTBackend) + obs = Observable{Union{Nothing, String}}(nothing) + active_tagger = back.active_tagger + on(active_tagger) do tagger + obs[] = isnothing(tagger) ? nothing : tagger.model_instance + end + on(obs) do model_instance + tagger = active_tagger[] + if model_instance != tagger.model_instance + active_tagger[] = back.taggers[tagger.backend][model_instance] + end + end + return obs +end + +function connect(back::LTBackend; refresh_rate=0.5, preselect_tagger=false) + while true + resp = HTTP.get("$(back.endpoint)/status") + resp = transcode(String, resp.body) + if resp == "up" + break + else + sleep(refresh_rate) + end + end + listtaggers(back) + #@info "listtaggers" back.taggers back.metadata + if preselect_tagger + back.active_tagging_backend[] = first(collect(keys(back.taggers))) + end +end + +function simpleconvert(json::JSON3.Object) + OrderedDict(key => simpleconvert(val) for (key, val) in pairs(json)) +end + +simpleconvert(json::JSON3.Array) = simpleconvert.(json) + +simpleconvert(val) = val + +function listtaggers(back::LTBackend) + endpoint = back.endpoint + resp = HTTP.get("$(endpoint)/list-taggers") + resp = transcode(String, resp.body) + json = JSON3.read(resp) + @assert json isa JSON3.Array + taggers = simpleconvert(json) + for tagger in taggers + tagging_backend = tagger[:name] + back.metadata[tagging_backend] = OrderedDict( + key => (key === :models ? Dict(model[:name] => OrderedDict( + key′=> val′ for (key′, val′) in pairs(model) if key′!== :name) + for model in val) : val) + for (key, val) in pairs(tagger) if key !== :name) + back.taggers[tagging_backend] = OrderedDict( + model[:name] => RemoteTagger(endpoint, tagging_backend, model[:name]) + for model in tagger[:models]) + end + return taggers +end + +listmodels(back::LTBackend) = listmodels(back, Val(false)) + +listmodels(back::LTBackend, ::Val{false}) = collect(keys(back.taggers)) + +function listmodels(back::LTBackend, ::Val{true}) + map(back.active_tagging_backend) do tagging_backend + isnothing(tagging_backend) ? String[] : collect(keys(back.taggers[tagging_backend])) + end +end + +function Taggers.predict(back::LTBackend, file::String; metadata=nothing) + tagger = back.active_tagger[] + isnothing(tagger) && throw("no active tagger") + connected(tagger) || connect!(tagger) + Taggers.push(tagger, file, metadata) + Taggers.predict(tagger) + labelfile = Taggers.pull(tagger, dirname(file)) + @assert length(labelfile) == 1 + return labelfile[1] +end + +end diff --git a/src/REST/Model.jl b/src/REST/Model.jl new file mode 100644 index 0000000..781ce7a --- /dev/null +++ b/src/REST/Model.jl @@ -0,0 +1,224 @@ +module Model + +import ..Taggers: Taggers, Tagger +import HTTP: HTTP +import JSON3 +using OrderedCollections: OrderedDict + +export LTBackend, gettoken, resetdata, listfiles, pushfile, pullfile, listtaggers, predict, + embed + +# pure part of the Server module (no global state) + +struct LTBackend + root + tokens + lock +end + +function LTBackend() + root = Ref{AbstractString}("") + tokens = Dict{String, Dict{String, Dict{String, Float64}}}() + lock = ReentrantLock() + LTBackend(root, tokens, lock) +end + +Base.lock(f::Function, backend::LTBackend) = lock(f, backend.lock) + +Base.isready(backend::LTBackend) = isdir(backend.root[]) + +get!(dict::AbstractDict{K, V}, key::K) where {K, V} = Base.get!(dict, key, V()) + +function get!(dict::AbstractDict{K, D}, key1::K, key2, keys...) where {K, D} + get!(get!(dict, key1), key2, keys...) +end + +function gettagger(lt_backend, tagging_backend_dir, model_instance) + @assert isready(lt_backend) + tagging_backend_path = joinpath(lt_backend.root[], tagging_backend_dir) + @assert Taggers.isbackend(tagging_backend_path) + lock(lt_backend) do + tagger = Taggers.isolate(Tagger(tagging_backend_path, model_instance)) + token = tagger.sandbox + tokens = get!(lt_backend.tokens, tagging_backend_dir, model_instance) + @assert token ∉ keys(tokens) + tokens[token] = time() + return tagger + end +end + +function gettagger(lt_backend, tagging_backend_dir, model_instance, token) + @assert isready(lt_backend) + lock(lt_backend) do + tokens = lt_backend.tokens + @assert tagging_backend_dir in keys(tokens) + tokens = lt_backend.tokens[tagging_backend_dir] + @assert model_instance in keys(tokens) + tokens = tokens[model_instance] + @assert token in keys(tokens) + end + tagging_backend_path = joinpath(lt_backend.root[], tagging_backend_dir) + tagger = Tagger(tagging_backend_path, model_instance, token) + return tagger +end + +## + +function gettoken(lt_backend, backend_dir, model_instance) + tagger = gettagger(lt_backend, backend_dir, model_instance) + return tagger.sandbox +end + +function Base.close(lt_backend::LTBackend, backend_dir, model_instance, token) + tagger = gettagger(lt_backend, backend_dir, model_instance, token) + Taggers.removedata(tagger) + lock(lt_backend) do + pop!(lt_backend.tokens[backend_dir][model_instance], token) + end + nothing +end + +function resetdata(lt_backend, backend_dir, model_instance, token, datadir=nothing) + tagger = gettagger(lt_backend, backend_dir, model_instance, token) + if isnothing(datadir) + Taggers.resetdata(tagger) + else + Taggers.resetdata(tagger, datadir) + end + nothing +end + +function listfiles(lt_backend, backend_dir, model_instance, token, data_dir) + tagger = gettagger(lt_backend, backend_dir, model_instance, token) + dir = Taggers.datadir(tagger, data_dir) + ls = [] + for (parent, _, files) in walkdir(dir; follow_symlinks=true) + if parent == dir + append!(ls, files) + else + parent = relpath(parent, dir) + for file in files + push!(ls, joinpath(parent, file)) + end + end + end + isempty(ls) ? "[]" : "[\"" * join(ls, "\", \"") * "\"]" +end + +""" + pushfile(::LTBackend, ::HTTP.Request, backend_dir, model_instance, token) + +Handle `push-file` queries, *i.e.* receive file. +""" +function pushfile(lt_backend, request, backend_dir, model_instance, token) + tagger = gettagger(lt_backend, backend_dir, model_instance, token) + @assert request.method == "POST" + body = request.body + @assert body isa Vector{UInt8} + k = findfirst(c -> c in (0x0d, 0x0a), body) - 1 + filesep = body[1:k] + linesep = if body[k+2] == 0x0a + @assert body[k+1] == 0x0d + body[k+1:k+2] + else + body[k+1] + end + filesep = vcat(linesep, filesep) + n = length(filesep) + dk = length(linesep) + bodies = Vector{UInt8}[] + while k < length(body) + i, j = 1, k + dk + 1 + for outer k in j:length(body) + if body[k] == filesep[i] + i += 1 + if n < i + push!(bodies, body[j:k-n]) + break + end + else + i = 1 + end + end + end + linesep = transcode(String, linesep) + for body in bodies + k = HTTP.Parsers.find_end_of_header(body) + @assert 0 < k + rawheader = transcode(String, body[1:k-2dk]) + content = body[k+1:end] + @debug "push-file" rawheader + header = Dict{Symbol, AbstractString}() + for line in split(rawheader, linesep) + if isempty(header) + for pair in split(line, "; ") + parts = split(pair, '"') + if length(parts) == 1 + key, val = split(pair, ": ") + header[Symbol(key)] = val + else + key = parts[1] + @assert endswith(key, '=') + key = Symbol(key[1:end-1]) + val = join(parts[2:end-1], '"') + header[key] = val + end + end + else + @assert startswith(line, "Content-Type: ") + key, val = split(line, ": ") + header[Symbol(key)] = val + end + end + @info "push-file" header length(content) + filename = header[:filename] + dest = joinpath(Taggers.datadir(tagger, "raw"), filename) + open(dest, "w") do f + write(f, content) + end + end +end + +function pullfile(lt_backend, backend_dir, model_instance, token, filename) + tagger = gettagger(lt_backend, backend_dir, model_instance, token) + src = joinpath(Taggers.datadir(tagger, "processed"), filename) + header = Dict("Content-Disposition" => "form-data") + body = open(src) + return HTTP.Response(200, header, body) +end + +function listtaggers(lt_backend) + inventory = Vector{OrderedDict{String, Any}}() + backends_dir = lt_backend.root[] + for tagging_backend in readdir(backends_dir) + tagging_backend_path = joinpath(backends_dir, tagging_backend) + Taggers.isbackend(tagging_backend_path) || continue + models_dir = joinpath(tagging_backend_path, "models") + models = [OrderedDict( + "name" => dir, + "description" => "", + "homepage" => "", + ) for dir in readdir(models_dir) if isdir(joinpath(models_dir, dir))] + push!(inventory, OrderedDict( + "name" => tagging_backend, + "description" => "", + "homepage" => "", + "models" => models, + )) + end + return JSON3.write(inventory) +end + +function predict(lt_backend, backend_dir, model_instance, token) + tagger = gettagger(lt_backend, backend_dir, model_instance, token) + # blocking; should we run async and expose a token-specific status api call? + Taggers.predict(tagger; skip_make_dataset=true) +end + +function embed(lt_backend, backend_dir, model_instance, token) + tagger = gettagger(lt_backend, backend_dir, model_instance, token) + # blocking, like predict + Taggers.embed(tagger; skip_make_dataset=true) +end + +end diff --git a/src/REST/REST.jl b/src/REST/REST.jl new file mode 100644 index 0000000..e4465b9 --- /dev/null +++ b/src/REST/REST.jl @@ -0,0 +1,8 @@ +module REST + +using ..Taggers + +include("Server.jl") +include("Client.jl") + +end diff --git a/src/REST/Server.jl b/src/REST/Server.jl new file mode 100644 index 0000000..4bd2bf5 --- /dev/null +++ b/src/REST/Server.jl @@ -0,0 +1,130 @@ +module Server + +using Oxygen; @oxidise +import ..Taggers + +include("Model.jl") +using .Model + +export run_backend + +function run_backend(backend::LTBackend; async=false, port=9285, kwargs...) + @assert isready(backend) + serve(; async=async, port=port, kwargs...) +end + +# the Oxygen module has global state; as a consequence, the server must also have global +# state +const lt_backend = LTBackend() + +function run_backend(root::AbstractString; kwargs...) + lt_backend.root[] = root + run_backend(; kwargs...) +end + +run_backend(; kwargs...) = run_backend(lt_backend; kwargs...) + + +@get "/status" function(request) + return "up" +end + + +@get "/get-token/{backend_dir}/{model_instance}" function( + request, + backend_dir::String, + model_instance::String, + ) + gettoken(lt_backend, backend_dir, model_instance) +end + + +@get "/close/{backend_dir}/{model_instance}/{token}" function( + request, + backend_dir::String, + model_instance::String, + token::String, + ) + close(lt_backend, backend_dir, model_instance, token) +end + + +@get "/reset-data/{backend_dir}/{model_instance}/{token}" function( + request, + backend_dir::String, + model_instance::String, + token::String, + ) + resetdata(lt_backend, backend_dir, model_instance, token) +end + + +@get "/reset-data/{backend_dir}/{model_instance}/{token}/{data_dir}" function( + request, + backend_dir::String, + model_instance::String, + token::String, + data_dir::String, + ) + resetdata(lt_backend, backend_dir, model_instance, token, data_dir) +end + + +@get "/list-files/{backend_dir}/{model_instance}/{token}/{data_dir}" function( + request, + backend_dir::String, + model_instance::String, + token::String, + data_dir::String, + ) + listfiles(lt_backend, backend_dir, model_instance, token, data_dir) +end + + +@post "/push-file/{backend_dir}/{model_instance}/{token}" function( + request, + backend_dir::String, + model_instance::String, + token::String, + ) + pushfile(lt_backend, request, backend_dir, model_instance, token) +end + + +@get "/pull-file/{backend_dir}/{model_instance}/{token}/{filename}" function( + request, + backend_dir::String, + model_instance::String, + token::String, + filename::String, + ) + pullfile(lt_backend, backend_dir, model_instance, token, filename) +end + + +@get "/list-taggers" function(request) + listtaggers(lt_backend) +end + + +@get "/predict/{backend_dir}/{model_instance}/{token}" function( + request, + backend_dir::String, + model_instance::String, + token::String, + ) + predict(lt_backend, backend_dir, model_instance, token) +end + + +@get "/embed/{backend_dir}/{model_instance}/{token}" function( + request, + backend_dir::String, + model_instance::String, + token::String, + ) + embed(lt_backend, backend_dir, model_instance, token) +end + + +end diff --git a/src/Taggers.jl b/src/Taggers.jl index b66ef40..e7864cc 100644 --- a/src/Taggers.jl +++ b/src/Taggers.jl @@ -11,14 +11,15 @@ struct Tagger output_filenames::Dict{String, String} end -function Tagger(backend_dir::String, model_instance::String) - Tagger(backend_dir, model_instance, nothing, Dict{String, String}()) +function Tagger(backend_dir::String, model_instance::String, + sandbox::Union{Nothing, String}=nothing) + Tagger(backend_dir, model_instance, sandbox, Dict{String, String}()) end Tagger(backend_dir, model_instance) = Tagger(string(backend_dir), string(model_instance)) function isolate(tagger) rawdatadir = joinpath(tagger.backend_dir, "data", "raw") - mkdir(rawdatadir) + isdir(rawdatadir) || mkpath(rawdatadir) rawdatadir = mktempdir(rawdatadir; cleanup=false) Tagger(tagger.backend_dir, tagger.model_instance, basename(rawdatadir), tagger.output_filenames) @@ -50,15 +51,15 @@ tagging_backend_command(tagger::Tagger) = tagging_backend_command(tagger.backend modeldir(tagger::Tagger) = joinpath(tagger.backend_dir, "models", tagger.model_instance) -datadir(tagger::Tagger, stage::String) = joinpath(tagger.backend_dir, "data", stage, +datadir(tagger::Tagger, stage) = joinpath(tagger.backend_dir, "data", stage, something(tagger.sandbox, tagger.model_instance)) -function reset(tagger::Tagger) +function reset(tagger) resetmodel(tagger) resetdata(tagger) end -function reset(dir::String) +function reset(dir::AbstractString) try rm(dir; recursive=true) catch @@ -69,13 +70,13 @@ end resetmodel(tagger::Tagger) = reset(modeldir(tagger)) -function resetdata(tagger::Tagger) +function resetdata(tagger) for dir in ("raw", "interim", "processed") resetdata(tagger, dir) end end -resetdata(tagger::Tagger, dir::String) = reset(datadir(tagger, dir)) +resetdata(tagger::Tagger, dir) = reset(datadir(tagger, dir)) function removedata(tagger::Tagger) for dir in ("raw", "interim", "processed") @@ -166,6 +167,72 @@ function push(tagger::Tagger, inputdata::String) return destination end +## new implementation for push + +function pushfile(tagger, src, dst) + backend_name = basename(realpath(tagger.backend_dir)) + @info "Pushing file to backend" backend=backend_name instance=tagger.model_instance src dst + src = normpath(src) + dst = normpath(joinpath(datadir(tagger, "raw"), dst)) + if dst != src + dstdir = dirname(dst) + mkpath(dstdir) + open(src, "r") do f + open(dst, "w") do g + write(g, read(f)) + end + end + end + return dst +end + +pushfile(tagger, src) = pushfile(tagger, src, basename(src)) + +function pushdir(tagger, src, dst=nothing) + raw = datadir(tagger, "raw") + dst = isnothing(dst) ? raw : joinpath(raw, dst) + symlink(src, dst) + return dst +end + +function push(tagger, inputdata::AbstractString) + destination = nothing + if occursin('*', inputdata) + repository = Dataloaders.Repository(inputdata) + for file in Formats.find_associated_files(Dataloaders.files(repository)) + srcfile = file.source + dstfile = relpath(srcfile, repository.root) + pushfile(tagger, srcfile, dstfile) + end + elseif isdir(inputdata) + srcdir = realpath(inputdata) # strip the end slashes + resetdata(tagger, "raw") + pushdir(tagger, srcdir) + elseif endswith(inputdata, ".txt") + files_by_dir = Dict{String, Vector{String}}() + for file in readlines(inputdata) + parent = dirname(file) + push!(get!(files_by_dir, parent, String[]), abspath(file)) + end + for (dir, files) in pairs(files_by_dir) + for file in Formats.find_associated_files(files) + srcfile = file.source + dstfile = joinpath(dir, basename(srcfile)) + pushfile(tagger, srcfile, dstfile) + end + end + else + for file in Formats.find_associated_files(abspath(inputdata)) + srcfile = file.source + dstfile = pushfile(tagger, srcfile) + if isnothing(destination) + destination = dstfile + end + end + end + return destination +end + function pull(tagger::Tagger, dest_dir::String) proc_data_dir = datadir(tagger, "processed") isdir(proc_data_dir) || throw("no processed data directory found") diff --git a/src/backends.jl b/src/backends.jl index 41f5c9b..d734ad1 100644 --- a/src/backends.jl +++ b/src/backends.jl @@ -46,26 +46,40 @@ Backends(controller, location) = Backends(controller, string(location)) function getbackends(controller, location=nothing) controller = gethub(controller) - try - return controller[:backends] - catch - backends = Backends(controller, location) - Observables.notify(backends.active_backend) - controller[:backends] = backends - return backends + if haskey(controller, :backends) + controller[:backends] + else + if !isnothing(location) && startswith(location, "http://") + back = REST.Client.LTBackend(location) + REST.Client.connect(back; preselect_tagger=true) + controller[:backends] = back + else + backends = Backends(controller, location) + Observables.notify(backends.active_backend) + controller[:backends] = backends + end end end -function Taggers.push(model::Backends, file::String; clean=true, metadata=true) +get_active_backend(backends::Backends) = backends.active_backend +get_model_instances(backends::Backends) = backends.model_instances +get_model_instance(backends::Backends) = backends.model_instance +get_backend_names(backends::Backends) = backends.backends + +get_active_backend(back::REST.Client.LTBackend) = back.active_tagging_backend +get_model_instances(back::REST.Client.LTBackend) = REST.Client.listmodels(back, Val(true)) +get_model_instance(back::REST.Client.LTBackend) = REST.Client.active_model_instance(back) +get_backend_names(back::REST.Client.LTBackend) = REST.Client.listmodels(back) + +function Taggers.push(model::Backends, file::String; clean=true, metadata=nothing) tagger = gettagger(model) clean ? resetdata(tagger) : resetdata(tagger, "raw") dest_file = Taggers.push(tagger, file) - if metadata + if !isnothing(metadata) # save the metadata to file, so that the backend can reproduce them in the output # file for predicted labels dest_file = joinpath(dirname(dest_file), "metadata") - metadata = Observables.to_value(getmetadatatable(model.controller)) - PlanarLarvae.Datasets.to_json_file(dest_file, asdict(metadata)) + PlanarLarvae.Datasets.to_json_file(dest_file, metadata) end end @@ -76,25 +90,32 @@ function Taggers.pull(model::Backends, destdir::String) return Taggers.pull(tagger, destdir) end -function Taggers.predict(model::Backends) +function Taggers.predict(model::Backends, file::String; metadata=nothing) isnothing(model.model_instance[]) && throw("no model selected") backend_dir = joinpath(model.location, model.active_backend[]) model_instance = model.model_instance[] isnothing(model_instance) && throw("no model instance selected") - turn_load_animation_on(model.controller) + tagger = Tagger(backend_dir, model_instance) + # + Taggers.push(model, file; metadata=metadata) + # TODO: make the skip_make_dataset option discoverable in the backend + predict(tagger; skip_make_dataset=true) + labelfile = Taggers.pull(model, dirname(file)) + @assert length(labelfile) == 1 + return labelfile[1] +end + +function Taggers.predict(controller::ControllerHub, back) + inputfile = controller[:input][] + isnothing(inputfile) && throw("no loaded files") + @assert ispath(inputfile) + metadata = asdict(Observables.to_value(getmetadatatable(controller))) + turn_load_animation_on(controller) try - # TODO: make the skip_make_dataset option discoverable in the backend - predict(Tagger(backend_dir, model_instance); skip_make_dataset=true) + resultingfile = predict(back, inputfile; metadata=metadata) + tryopenfile(controller, resultingfile; reload=true) catch - turn_load_animation_off(model.controller) + turn_load_animation_off(controller) rethrow() end end - -function Taggers.predict(model::Backends, file::String) - Taggers.push(model, file) - predict(model) - labelfile = Taggers.pull(model, dirname(file)) - @assert length(labelfile) == 1 - tryopenfile(model.controller, labelfile[1]; reload=true) -end diff --git a/src/cli_open.jl b/src/cli_open.jl index a1d46b6..73210d8 100644 --- a/src/cli_open.jl +++ b/src/cli_open.jl @@ -54,7 +54,7 @@ function main(args=ARGS; exit_on_error=false) infile = parsed_args["<file-path>"] if isempty(infile) infile = nothing - elseif !isfile(infile) + elseif !(startswith(infile, "http://") || isfile(infile)) if isdir(infile) dataroot = infile infile = nothing diff --git a/src/editor.jl b/src/editor.jl index ad40fb6..4891530 100644 --- a/src/editor.jl +++ b/src/editor.jl @@ -43,6 +43,11 @@ function larvaeditor(path=nothing; enable_delete=false, kwargs...) + if path isa AbstractString && startswith(path, "http://") + backend_directory = path + path = nothing + end + # to (re-)load a file, the app is reloaded with the filepath as sole information # from previous session T = Ref{Union{Nothing, String}} diff --git a/src/larvatagger.css b/src/larvatagger.css index 013b8a4..943cd77 100644 --- a/src/larvatagger.css +++ b/src/larvatagger.css @@ -146,7 +146,8 @@ table { } button:disabled { - --text-opacity: 0.5; + /* --text-opacity: 0.5; */ + opacity: 0.5; pointer-events: none; } diff --git a/src/wgl.jl b/src/wgl.jl index fb4640d..6674dc5 100644 --- a/src/wgl.jl +++ b/src/wgl.jl @@ -979,33 +979,39 @@ function addtosavequeue!(c::LarvaFilter, id) end struct BackendMenu - backends::Backends + backends + models send2backend::NyxWidgets.Button dom_id end function backendmenu(controller, location) + controller = gethub(controller) backends = getbackends(controller, location) - disabled = map(isempty, backends.model_instances) + models = get_model_instances(backends) + disabled = if isnothing(controller[:input][]) + true + else + map(isempty, models) + end send2backend = NyxWidgets.Button("Autotag"; disabled=disabled) on(send2backend) do _ - predict(backends, controller[:input][]) + predict(controller, backends) end - BackendMenu(backends, send2backend, dom_id()) + BackendMenu(backends, models, send2backend, dom_id()) end function lowerdom(bs::BackendMenu) - models = bs.backends.model_instances - model_instance = bs.backends.model_instance + model_instance = get_model_instance(bs.backends) update_model_instance = js"(evt)=>{ $model_instance.notify(evt.srcElement.value); }" - select_dom = DOM.select(DOM.option(model; value=model) for model in models[]; + select_dom = DOM.select(DOM.option(model; value=model) for model in bs.models[]; onchange=update_model_instance, class=css_button) - active_backend = bs.backends.active_backend + active_backend = get_active_backend(bs.backends) update_active_backend = js"(evt)=>{ $active_backend.notify(evt.srcElement.value); }" return DOM.div(DOM.label("Backend"), DOM.select(DOM.option(backend; value=backend) - for backend in bs.backends.backends; + for backend in get_backend_names(bs.backends); onchange=update_active_backend, class=css_button), DOM.label("Model instance"), @@ -1015,7 +1021,7 @@ function lowerdom(bs::BackendMenu) end function Bonito.jsrender(session::Session, bs::BackendMenu) node = lowerdom(session, bs) - onjs(session, bs.backends.model_instances, js"""(options) => { + onjs(session, bs.models, js"""(options) => { select = document.querySelectorAll($(dom_selector(bs)) + ' > select')[1]; LarvaTagger.updateSelectOptions(select, options); }""") diff --git a/test/rest_client.sh b/test/rest_client.sh new file mode 100755 index 0000000..23daccb --- /dev/null +++ b/test/rest_client.sh @@ -0,0 +1,32 @@ +#!/bin/bash + +set -m + +this_script=$(realpath "${BASH_SOURCE[0]}") +larvatagger_jl_project_root=$(dirname "$(dirname "${this_script}")") +larvatagger_project_root=$(dirname "${larvatagger_jl_project_root}") + +tagging_backend=MaggotUBA +tagging_model=20230311 +lt_backend_port=9285 + +# pre-requisites are similar to rest_server.sh + +# pre-compile +julia +1.10 --project="${larvatagger_jl_project_root}" -q -e "using LarvaTagger" + +# run and background the backend server +JULIA_PROJECT="${larvatagger_project_root}/TaggingBackends" \ + julia +1.10 --project="${larvatagger_jl_project_root}" -i \ + -e "using LarvaTagger.REST.Server; run_backend(\"${larvatagger_project_root}\"; port=${lt_backend_port})" & +lt_backend_pid=$! + +# run the frontend server +JULIA="julia +1.10" ${larvatagger_jl_project_root}/scripts/larvatagger-gui.jl http://localhost:${lt_backend_port} + +# scenarii: +# * click on "Autotag" prior to loading any files (if not disabled, as with a bug in v0.19) +# * load a tracking data file, and then click on "Autotag" + +kill $lt_backend_pid +wait $lt_backend_pid diff --git a/test/rest_server.sh b/test/rest_server.sh new file mode 100755 index 0000000..6de171f --- /dev/null +++ b/test/rest_server.sh @@ -0,0 +1,177 @@ +#!/bin/bash + +set -m + +this_script=$(realpath "${BASH_SOURCE[0]}") +larvatagger_jl_project_root=$(dirname "$(dirname "${this_script}")") +larvatagger_project_root=$(dirname "${larvatagger_jl_project_root}") + +tagging_backend=MaggotUBA +tagging_model=20230311 +lt_backend_port=9285 + +# assumed directory structure: +# the MaggotUBA-adapter, TaggingBackends, NyxArtefacts and LarvaTagger.jl projects are siblings in the ${larvatagger_project_root} directory; +# the MaggotUBA-adapter project is available both as directory MaggotUBA-adapter and link MaggotUBA (${tagging_backend}); +# the MaggotUBA-adapter tagging backend contains two trained models (or model instances): 20230311 and 20230311-0; +# the NyxArtefacts project is available as directory Artefacts; +# MaggotUBA is installed with JULIA_PROJECT pointing at the TaggingBackends directory + +[ -d "${larvatagger_project_root}/${tagging_backend}/models/${tagging_model}" ] || exit "tagging backend or model not found" + +if [ -z "`julia +1.10 -v 2>/dev/null`" ]; then + juliaup add 1.10 +fi + +# run and background the backend server +JULIA_PROJECT="${larvatagger_project_root}/TaggingBackends" \ + julia +1.10 --project="${larvatagger_jl_project_root}" -iq \ + -e "using LarvaTagger.REST.Server; run_backend(\"${larvatagger_project_root}\"; port=${lt_backend_port})" & +lt_backend_pid=$! + +# wait for the server to be ready +while [ "`curl -s http://localhost:${lt_backend_port}/status`" != "up" ]; do + sleep 1 +done +echo "status: success" + +# get a session token for a tagging backend +token=`curl -sS http://localhost:${lt_backend_port}/get-token/${tagging_backend}/${tagging_model}` + +if [ "${token:0:3}" = "jl_" ]; then + echo "get-token: success" +else + echo "get-token: failure" + echo "expected: string starting with \"jl_\"" + echo "got: $token" +fi + +# send one text file, one binary file +curl -sS -F "f=@${larvatagger_jl_project_root}/README.md" -F "g=@${larvatagger_project_root}/Artefacts/PlanarLarvae/trx_small.tgz" http://localhost:${lt_backend_port}/push-file/${tagging_backend}/${tagging_model}/${token} 1>/dev/null + +generated_files=(`ls "${larvatagger_project_root}/${tagging_backend}/data/raw/${token}"`) + +expected_files=("README.md" "trx_small.tgz") + +if [ ${#generated_files[@]} -eq ${#expected_files[@]} -a \ + "${generated_files[0]}" = "${expected_files[0]}" -a \ + "${generated_files[1]}" = "${expected_files[1]}" ]; then + echo "push-file: success" +else + echo "push-file: failure" +fi + +# discover the sent files +discovered_files=`curl -sS http://localhost:${lt_backend_port}/list-files/${tagging_backend}/${tagging_model}/${token}/raw` + +expected_files='["README.md", "trx_small.tgz"]' + +if [ "$discovered_files" = "$expected_files" ]; then + echo "list-files: success" +else + echo "list-files: failure" + echo "expected: $expected_files" + echo "got: $discovered_files" +fi + +# make file in processed data dir +test_filename=label.json + +mkdir -p "${larvatagger_project_root}/${tagging_backend}/data/processed/${token}" +cat <<EOF >"${larvatagger_project_root}/${tagging_backend}/data/processed/${token}/${test_filename}" +{ +} +EOF + +# retrieve file from processed data dir +retrieved_content=`curl -sS http://localhost:${lt_backend_port}/pull-file/${tagging_backend}/${tagging_model}/${token}/${test_filename}` + +expected_content="{ +}" + +if [ "$retrieved_content" = "$expected_content" ]; then + echo "pull-file: success" +else + echo "pull-file: failure" + echo "expected file content:" + echo "$expected_content" + echo "got:" + echo "$retrieved_content" +fi + +# request file deletion +curl -sS http://localhost:${lt_backend_port}/reset-data/${tagging_backend}/${tagging_model}/${token}/raw 1>/dev/null + +stored_files=`ls "${larvatagger_project_root}/${tagging_backend}/data/raw/${token}/"` +if [ -z "$stored_files" ]; then + echo "reset-data: success" +else + echo "reset-data: failure" + echo "expected empty list" + echo "got:" + echo "$stored_files" +fi + +# discover the backend(s) and their models +discovered_backends=`curl -sS http://localhost:${lt_backend_port}/list-backends` + +backend_metadata() { + local desc1= + local link1= + local desc2= + local link2= + local desc3= + local link3= + echo "{\"name\":\"$1\",\"description\":\"$desc1\",\"homepage\":\"$link1\",\"models\":[{\"name\":\"20230311\",\"description\":\"$desc2\",\"homepage\":\"$link2\"},{\"name\":\"20230311-0\",\"description\":\"$desc3\",\"homepage\":\"$link3\"}]}" +} +expected_backends="[`backend_metadata $tagging_backend`,`backend_metadata ${tagging_backend}-adapter`]" + +if [ "$discovered_backends" = "$expected_backends" ]; then + echo "list-backends: success" +else + echo "list-backends: failure" + echo "expected:" + echo "$expected_backends" + echo "got:" + echo "$discovered_backends" + # further diagnose + model_instances=(`ls "${larvatagger_project_root}/${tagging_backend}/models"`) + if ! [ ${#model_instances[@]} -eq 2 -a "${model_instances[0]}" = "20230311" -a "${model_instances[1]}" = "20230311-0" ]; then + echo "tagging backend is not adequately set up" + fi +fi + +cp "${larvatagger_jl_project_root}"/20140805_101522@FCF_attP2_1500062@UAS_TNT_2_0003@t5@p_8_45s1x30s0s#p_8_105s10x2s10s#n#n@100.* "${larvatagger_project_root}/${tagging_backend}/data/raw/${token}/" + +# if python does not find TaggingBackends, refresh LT install: +#(cd ../MaggotUBA-adapter && (cd ../TaggingBackends && PYTHON="`poetry env info`/bin/python" julia +1.10 --project=. -e 'using Pkg; Pkg.instantiate()')) +#(cd ../MaggotUBA-adapter && JULIA_PROJECT="`realpath ../TaggingBackends`" poetry install) + +# run the predict function of the tagging backend +curl -sS http://localhost:${lt_backend_port}/predict/${tagging_backend}/${tagging_model}/${token} 1>/dev/null + +generated_files=(`ls "${larvatagger_project_root}/${tagging_backend}/data/processed/${token}/"`) + +if [ ${#generated_files[@]} = 1 -a "${generated_files[0]}" = "predicted.label" ]; then + echo "predict: success" +else + echo "predict: failure" + echo "expected: predicted.label" + echo "got:" + echo "$generated_files" +fi + +# clear session data +curl -sS http://localhost:${lt_backend_port}/close/${tagging_backend}/${tagging_model}/${token} 1>/dev/null + +if ! [ -d "${larvatagger_project_root}/${tagging_backend}/data/raw/${token}" ] && \ + ! [ -d "${larvatagger_project_root}/${tagging_backend}/data/interim/${token}" ] && \ + ! [ -d "${larvatagger_project_root}/${tagging_backend}/data/processed/${token}" ]; then + echo "close: success" +else + echo "close: failure" +fi + +echo "tests complete; terminating the backend (a stack trace will follow)" +kill $lt_backend_pid +wait $lt_backend_pid -- GitLab From 53a879ee638b99ba90f0caeb15b585635a3be8e5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=C3=A7ois=20Laurent?= <francois.laurent@posteo.net> Date: Mon, 31 Mar 2025 11:48:11 +0200 Subject: [PATCH 3/8] feat: REST api --- Manifest-v1.11.toml | 523 +++++++++++++++++++++++--------------------- Manifest.toml | 474 ++++++++++++++++++++------------------- src/REST/Client.jl | 12 +- test/rest_client.sh | 17 +- 4 files changed, 543 insertions(+), 483 deletions(-) diff --git a/Manifest-v1.11.toml b/Manifest-v1.11.toml index 53ceb33..4a3fd72 100644 --- a/Manifest-v1.11.toml +++ b/Manifest-v1.11.toml @@ -1,8 +1,8 @@ # This file is machine-generated - editing it directly is not advised -julia_version = "1.11.3" +julia_version = "1.11.4" manifest_format = "2.0" -project_hash = "423cfe5e2b370a6df6f85f87fd1406fd07136176" +project_hash = "ba336c605739d728e2989784d94690e67b22a25d" [[deps.AbstractFFTs]] deps = ["LinearAlgebra"] @@ -22,12 +22,13 @@ version = "0.4.5" [[deps.Adapt]] deps = ["LinearAlgebra", "Requires"] -git-tree-sha1 = "50c3c56a52972d78e8be9fd135bfb91c9574c140" +git-tree-sha1 = "f7817e2e585aa6d924fd714df1e2a84be7896c60" uuid = "79e6a3ab-5dfb-504d-930d-738a2a938a0e" -version = "4.1.1" -weakdeps = ["StaticArrays"] +version = "4.3.0" +weakdeps = ["SparseArrays", "StaticArrays"] [deps.Adapt.extensions] + AdaptSparseArraysExt = "SparseArrays" AdaptStaticArraysExt = "StaticArrays" [[deps.AdaptivePredicates]] @@ -43,9 +44,9 @@ version = "1.1.3" [[deps.Animations]] deps = ["Colors"] -git-tree-sha1 = "e81c509d2c8e49592413bfb0bb3b08150056c79d" +git-tree-sha1 = "e092fa223bf66a3c41f9c022bd074d916dc303e7" uuid = "27a7e980-b3e6-11e9-2bcd-0b925532e340" -version = "0.4.1" +version = "0.4.2" [[deps.ArgTools]] uuid = "0dad84c5-d112-42e6-8d28-ef12dabb789f" @@ -99,10 +100,10 @@ uuid = "e1450e63-4bb3-523b-b2a4-4ffa8c0fd77d" version = "1.2.2" [[deps.Bzip2_jll]] -deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg"] -git-tree-sha1 = "8873e196c2eb87962a2048b3b8e08946535864a1" +deps = ["Artifacts", "JLLWrappers", "Libdl"] +git-tree-sha1 = "1b96ea4a01afe0ea4090c5c8039690672dd13f2e" uuid = "6e34b625-4abd-537c-b88f-471c36dfa7a0" -version = "1.0.8+2" +version = "1.0.9+0" [[deps.CEnum]] git-tree-sha1 = "389ad5c84de1ae7cf0e28e381131c98ea87d54fc" @@ -121,15 +122,15 @@ version = "1.0.1+0" [[deps.Cairo_jll]] deps = ["Artifacts", "Bzip2_jll", "CompilerSupportLibraries_jll", "Fontconfig_jll", "FreeType2_jll", "Glib_jll", "JLLWrappers", "LZO_jll", "Libdl", "Pixman_jll", "Xorg_libXext_jll", "Xorg_libXrender_jll", "Zlib_jll", "libpng_jll"] -git-tree-sha1 = "009060c9a6168704143100f36ab08f06c2af4642" +git-tree-sha1 = "2ac646d71d0d24b44f3f8c84da8c9f4d70fb67df" uuid = "83423d85-b0ee-5818-9007-b63ccbeb887a" -version = "1.18.2+1" +version = "1.18.4+0" [[deps.ChainRulesCore]] deps = ["Compat", "LinearAlgebra"] -git-tree-sha1 = "3e4b134270b372f2ed4d4d0e936aabaefc1802bc" +git-tree-sha1 = "1713c74e00545bfe14605d2a2be1712de8fbcb58" uuid = "d360d2e6-b24c-11e9-a2a3-2a2ae2dbcce4" -version = "1.25.0" +version = "1.25.1" weakdeps = ["SparseArrays"] [deps.ChainRulesCore.extensions] @@ -143,33 +144,37 @@ version = "1.4.0" [[deps.CodecZlib]] deps = ["TranscodingStreams", "Zlib_jll"] -git-tree-sha1 = "bce6804e5e6044c6daab27bb533d1295e4a2e759" +git-tree-sha1 = "962834c22b66e32aa10f7611c08c8ca4e20749a9" uuid = "944b1d66-785c-5afd-91f1-9de20f533193" -version = "0.7.6" +version = "0.7.8" [[deps.ColorBrewer]] -deps = ["Colors", "JSON", "Test"] -git-tree-sha1 = "61c5334f33d91e570e1d0c3eb5465835242582c4" +deps = ["Colors", "JSON"] +git-tree-sha1 = "e771a63cc8b539eca78c85b0cabd9233d6c8f06f" uuid = "a2cac450-b92f-5266-8821-25eda20663c8" -version = "0.4.0" +version = "0.4.1" [[deps.ColorSchemes]] deps = ["ColorTypes", "ColorVectorSpace", "Colors", "FixedPointNumbers", "PrecompileTools", "Random"] -git-tree-sha1 = "13951eb68769ad1cd460cdb2e64e5e95f1bf123d" +git-tree-sha1 = "403f2d8e209681fcbd9468a8514efff3ea08452e" uuid = "35d6a980-a343-548e-a6ea-1d62b119f2f4" -version = "3.27.0" +version = "3.29.0" [[deps.ColorTypes]] deps = ["FixedPointNumbers", "Random"] -git-tree-sha1 = "b10d0b65641d57b8b4d5e234446582de5047050d" +git-tree-sha1 = "c7acce7a7e1078a20a285211dd73cd3941a871d6" uuid = "3da002f7-5984-5a60-b8a6-cbb66c0b333f" -version = "0.11.5" +version = "0.12.0" +weakdeps = ["StyledStrings"] + + [deps.ColorTypes.extensions] + StyledStringsExt = "StyledStrings" [[deps.ColorVectorSpace]] deps = ["ColorTypes", "FixedPointNumbers", "LinearAlgebra", "Requires", "Statistics", "TensorCore"] -git-tree-sha1 = "a1f44953f2382ebb937d60dafbe2deea4bd23249" +git-tree-sha1 = "8b3b6f87ce8f65a2b4f857528fd8d70086cd72b1" uuid = "c3611d14-8923-5661-9e6a-0046d554d3a4" -version = "0.10.0" +version = "0.11.0" weakdeps = ["SpecialFunctions"] [deps.ColorVectorSpace.extensions] @@ -177,9 +182,9 @@ weakdeps = ["SpecialFunctions"] [[deps.Colors]] deps = ["ColorTypes", "FixedPointNumbers", "Reexport"] -git-tree-sha1 = "362a287c3aa50601b0bc359053d5c2468f0e7ce0" +git-tree-sha1 = "64e15186f0aa277e174aa81798f7eb8598e0157e" uuid = "5ae59095-9a9b-59fe-a467-6f913c188581" -version = "0.12.11" +version = "0.13.0" [[deps.Compat]] deps = ["TOML", "UUIDs"] @@ -198,9 +203,9 @@ version = "1.1.1+0" [[deps.ConcurrentUtilities]] deps = ["Serialization", "Sockets"] -git-tree-sha1 = "ea32b83ca4fefa1768dc84e504cc0a94fb1ab8d1" +git-tree-sha1 = "d9d26935a0bcffc87d2613ce14c527c99fc543fd" uuid = "f0e56b4a-5159-44fe-b623-3e5288b988bb" -version = "2.4.2" +version = "2.5.0" [[deps.ConstructionBase]] git-tree-sha1 = "76219f1ed5771adbb096743bff43fb5fdd4c1157" @@ -225,9 +230,9 @@ version = "1.16.0" [[deps.DataStructures]] deps = ["Compat", "InteractiveUtils", "OrderedCollections"] -git-tree-sha1 = "1d0a14036acb104d9e89698bd408f63ab58cdc82" +git-tree-sha1 = "4e1fe97fdaed23e9dc21d4d664bea76b65fc50a0" uuid = "864edb3b-99cc-5e75-8d2d-829cb0a9cfe8" -version = "0.18.20" +version = "0.18.22" [[deps.DataValueInterfaces]] git-tree-sha1 = "bfc1187b79289637fa0ef6d4436ebdfe6905cbd6" @@ -240,10 +245,10 @@ uuid = "ade2ca70-3891-5945-98fb-dc099432e06a" version = "1.11.0" [[deps.DelaunayTriangulation]] -deps = ["AdaptivePredicates", "EnumX", "ExactPredicates", "PrecompileTools", "Random"] -git-tree-sha1 = "89df54fbe66e5872d91d8c2cd3a375f660c3fd64" +deps = ["AdaptivePredicates", "EnumX", "ExactPredicates", "Random"] +git-tree-sha1 = "5620ff4ee0084a6ab7097a27ba0c19290200b037" uuid = "927a84f5-c5f4-47a5-9785-b46e178433df" -version = "1.6.1" +version = "1.6.4" [[deps.DelimitedFiles]] deps = ["Mmap"] @@ -275,9 +280,9 @@ version = "1.11.0" [[deps.Distributions]] deps = ["AliasTables", "FillArrays", "LinearAlgebra", "PDMats", "Printf", "QuadGK", "Random", "SpecialFunctions", "Statistics", "StatsAPI", "StatsBase", "StatsFuns"] -git-tree-sha1 = "3101c32aab536e7a27b1763c0797dba151b899ad" +git-tree-sha1 = "0b4190661e8a4e51a842070e7dd4fae440ddb7f4" uuid = "31c24e10-a181-5473-b8eb-7969acd0382f" -version = "0.25.113" +version = "0.25.118" [deps.Distributions.extensions] DistributionsChainRulesCoreExt = "ChainRulesCore" @@ -296,10 +301,9 @@ uuid = "968ba79b-81e4-546f-ab3a-2eecfa62a9db" version = "0.5.0" [[deps.DocStringExtensions]] -deps = ["LibGit2"] -git-tree-sha1 = "2fb1e02f2b635d0845df5d7c167fec4dd739b00d" +git-tree-sha1 = "e7b7e6f178525d17c720ab9c081e4ef04429f860" uuid = "ffbed154-4ef7-542d-bbb7-c09d3a79fcae" -version = "0.9.3" +version = "0.9.4" [[deps.Downloads]] deps = ["ArgTools", "FileWatching", "LibCURL", "NetworkOptions"] @@ -313,9 +317,9 @@ uuid = "5ae413db-bbd1-5e63-b57d-d24a61df00f5" version = "2.2.4+0" [[deps.EnumX]] -git-tree-sha1 = "bdb1942cd4c45e3c678fd11569d5cccd80976237" +git-tree-sha1 = "bddad79635af6aec424f53ed8aad5d7555dc6f00" uuid = "4e289a0a-7415-4d19-859d-a7e5c4648b56" -version = "1.0.4" +version = "1.0.5" [[deps.ExactPredicates]] deps = ["IntervalArithmetic", "Random", "StaticArrays"] @@ -325,20 +329,20 @@ version = "2.2.8" [[deps.ExceptionUnwrapping]] deps = ["Test"] -git-tree-sha1 = "dcb08a0d93ec0b1cdc4af184b26b591e9695423a" +git-tree-sha1 = "d36f682e590a83d63d1c7dbd287573764682d12a" uuid = "460bff9d-24e4-43bc-9d9f-a8973cb893f4" -version = "0.1.10" +version = "0.1.11" [[deps.Expat_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "1c6317308b9dc757616f0b5cb379db10494443a7" +git-tree-sha1 = "d55dffd9ae73ff72f1c0482454dcf2ec6c6c4a63" uuid = "2e619515-83b5-522b-bb60-26c02a35a201" -version = "2.6.2+0" +version = "2.6.5+0" [[deps.Extents]] -git-tree-sha1 = "81023caa0021a41712685887db1fc03db26f41f5" +git-tree-sha1 = "063512a13dbe9c40d999c439268539aa552d1ae6" uuid = "411431e0-e8b7-467b-b5e0-f676ba4f2910" -version = "0.1.4" +version = "0.1.5" [[deps.FFMPEG_jll]] deps = ["Artifacts", "Bzip2_jll", "FreeType2_jll", "FriBidi_jll", "JLLWrappers", "LAME_jll", "Libdl", "Ogg_jll", "OpenSSL_jll", "Opus_jll", "PCRE2_jll", "Zlib_jll", "libaom_jll", "libass_jll", "libfdk_aac_jll", "libvorbis_jll", "x264_jll", "x265_jll"] @@ -348,21 +352,25 @@ version = "6.1.2+0" [[deps.FFTW]] deps = ["AbstractFFTs", "FFTW_jll", "LinearAlgebra", "MKL_jll", "Preferences", "Reexport"] -git-tree-sha1 = "4820348781ae578893311153d69049a93d05f39d" +git-tree-sha1 = "7de7c78d681078f027389e067864a8d53bd7c3c9" uuid = "7a1cc6ca-52ef-59f5-83cd-3a7055c09341" -version = "1.8.0" +version = "1.8.1" [[deps.FFTW_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg"] git-tree-sha1 = "4d81ed14783ec49ce9f2e168208a12ce1815aa25" uuid = "f5851436-0d7a-5f13-b9de-f02708fd171a" -version = "3.3.10+1" +version = "3.3.10+3" [[deps.FileIO]] deps = ["Pkg", "Requires", "UUIDs"] -git-tree-sha1 = "62ca0547a14c57e98154423419d8a342dca75ca9" +git-tree-sha1 = "b66970a70db13f45b7e57fbda1736e1cf72174ea" uuid = "5789e2e9-d7fb-5bc7-8068-2c6fae9b9549" -version = "1.16.4" +version = "1.17.0" +weakdeps = ["HTTP"] + + [deps.FileIO.extensions] + HTTPExt = "HTTP" [[deps.FilePaths]] deps = ["FilePathsBase", "MacroTools", "Reexport", "Requires"] @@ -372,9 +380,9 @@ version = "0.8.3" [[deps.FilePathsBase]] deps = ["Compat", "Dates"] -git-tree-sha1 = "7878ff7172a8e6beedd1dea14bd27c3c6340d361" +git-tree-sha1 = "3bab2c5aa25e7840a4b065805c0cdfc01f3068d2" uuid = "48062228-2e41-5def-b9a4-89aafe57970f" -version = "0.9.22" +version = "0.9.24" weakdeps = ["Mmap", "Test"] [deps.FilePathsBase.extensions] @@ -405,9 +413,9 @@ version = "0.8.5" [[deps.Fontconfig_jll]] deps = ["Artifacts", "Bzip2_jll", "Expat_jll", "FreeType2_jll", "JLLWrappers", "Libdl", "Libuuid_jll", "Zlib_jll"] -git-tree-sha1 = "db16beca600632c95fc8aca29890d83788dd8b23" +git-tree-sha1 = "21fac3c77d7b5a9fc03b0ec503aa1a6392c34d2b" uuid = "a3f928ae-7b40-5064-980b-68af3947d34b" -version = "2.13.96+0" +version = "2.15.0+0" [[deps.Format]] git-tree-sha1 = "9c68794ef81b08086aeb32eeaf33531668d5f5fc" @@ -422,38 +430,38 @@ version = "4.1.1" [[deps.FreeType2_jll]] deps = ["Artifacts", "Bzip2_jll", "JLLWrappers", "Libdl", "Zlib_jll"] -git-tree-sha1 = "5c1d8ae0efc6c2e7b1fc502cbe25def8f661b7bc" +git-tree-sha1 = "2c5512e11c791d1baed2049c5652441b28fc6a31" uuid = "d7e528f0-a631-5988-bf34-fe36492bcfd7" -version = "2.13.2+0" +version = "2.13.4+0" [[deps.FreeTypeAbstraction]] deps = ["ColorVectorSpace", "Colors", "FreeType", "GeometryBasics"] -git-tree-sha1 = "84dfe824bd6fdf2a5d73bb187ff31b5549b2a79c" +git-tree-sha1 = "d52e255138ac21be31fa633200b65e4e71d26802" uuid = "663a7486-cb36-511b-a19d-713bb74d65c9" -version = "0.10.4" +version = "0.10.6" [[deps.FriBidi_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "1ed150b39aebcc805c26b93a8d0122c940f64ce2" +git-tree-sha1 = "846f7026a9decf3679419122b49f8a1fdb48d2d5" uuid = "559328eb-81f9-559d-9380-de523a88c83c" -version = "1.0.14+0" +version = "1.0.16+0" [[deps.GeoFormatTypes]] -git-tree-sha1 = "59107c179a586f0fe667024c5eb7033e81333271" +git-tree-sha1 = "8e233d5167e63d708d41f87597433f59a0f213fe" uuid = "68eda718-8dee-11e9-39e7-89f7f65f511f" -version = "0.4.2" +version = "0.4.4" [[deps.GeoInterface]] -deps = ["Extents", "GeoFormatTypes"] -git-tree-sha1 = "826b4fd69438d9ce4d2b19de6bc2f970f45f0f88" +deps = ["DataAPI", "Extents", "GeoFormatTypes"] +git-tree-sha1 = "294e99f19869d0b0cb71aef92f19d03649d028d5" uuid = "cf35fbd7-0cd7-5166-be24-54bfbe79505f" -version = "1.3.8" +version = "1.4.1" [[deps.GeometryBasics]] -deps = ["EarCut_jll", "Extents", "GeoInterface", "IterTools", "LinearAlgebra", "StaticArrays", "StructArrays", "Tables"] -git-tree-sha1 = "b62f2b2d76cee0d61a2ef2b3118cd2a3215d3134" +deps = ["EarCut_jll", "Extents", "GeoInterface", "IterTools", "LinearAlgebra", "PrecompileTools", "Random", "StaticArrays"] +git-tree-sha1 = "65e3f5c519c3ec6a4c59f4c3ba21b6ff3add95b0" uuid = "5c1252a2-5f33-56bf-86c9-59e7332b4326" -version = "0.4.11" +version = "0.5.7" [[deps.Gettext_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "Libdl", "Libiconv_jll", "Pkg", "XML2_jll"] @@ -463,27 +471,27 @@ version = "0.21.0+0" [[deps.Giflib_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "0224cce99284d997f6880a42ef715a37c99338d1" +git-tree-sha1 = "6570366d757b50fabae9f4315ad74d2e40c0560a" uuid = "59f7168a-df46-5410-90c8-f2779963d0ec" -version = "5.2.2+0" +version = "5.2.3+0" [[deps.Glib_jll]] deps = ["Artifacts", "Gettext_jll", "JLLWrappers", "Libdl", "Libffi_jll", "Libiconv_jll", "Libmount_jll", "PCRE2_jll", "Zlib_jll"] -git-tree-sha1 = "674ff0db93fffcd11a3573986e550d66cd4fd71f" +git-tree-sha1 = "b0036b392358c80d2d2124746c2bf3d48d457938" uuid = "7746bdde-850d-59dc-9ae8-88ece973131d" -version = "2.80.5+0" +version = "2.82.4+0" [[deps.Graphite2_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg"] -git-tree-sha1 = "344bf40dcab1073aca04aa0df4fb092f920e4011" +git-tree-sha1 = "01979f9b37367603e2848ea225918a3b3861b606" uuid = "3b182d85-2403-5c21-9c21-1e1f0cc25472" -version = "1.3.14+0" +version = "1.3.14+1" [[deps.GridLayoutBase]] deps = ["GeometryBasics", "InteractiveUtils", "Observables"] -git-tree-sha1 = "fc713f007cff99ff9e50accba6373624ddd33588" +git-tree-sha1 = "dc6bed05c15523624909b3953686c5f5ffa10adc" uuid = "3955a311-db13-416c-9275-1d80ed98e5e9" -version = "0.11.0" +version = "0.11.1" [[deps.Grisu]] git-tree-sha1 = "53bb909d1151e57e2484c3d1b53e19552b887fb2" @@ -503,34 +511,34 @@ version = "0.17.2" MPI = "da04e1cc-30fd-572f-bb4f-1f8673147195" [[deps.HDF5_jll]] -deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "LLVMOpenMP_jll", "LazyArtifacts", "LibCURL_jll", "Libdl", "MPICH_jll", "MPIPreferences", "MPItrampoline_jll", "MicrosoftMPI_jll", "OpenMPI_jll", "OpenSSL_jll", "TOML", "Zlib_jll", "libaec_jll"] -git-tree-sha1 = "38c8874692d48d5440d5752d6c74b0c6b0b60739" +deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "LazyArtifacts", "LibCURL_jll", "Libdl", "MPICH_jll", "MPIPreferences", "MPItrampoline_jll", "MicrosoftMPI_jll", "OpenMPI_jll", "OpenSSL_jll", "TOML", "Zlib_jll", "libaec_jll"] +git-tree-sha1 = "e94f84da9af7ce9c6be049e9067e511e17ff89ec" uuid = "0234f1f7-429e-5d53-9886-15a909be8d59" -version = "1.14.2+1" +version = "1.14.6+0" [[deps.HTTP]] -deps = ["Base64", "CodecZlib", "ConcurrentUtilities", "Dates", "ExceptionUnwrapping", "Logging", "LoggingExtras", "MbedTLS", "NetworkOptions", "OpenSSL", "Random", "SimpleBufferStream", "Sockets", "URIs", "UUIDs"] -git-tree-sha1 = "bc3f416a965ae61968c20d0ad867556367f2817d" +deps = ["Base64", "CodecZlib", "ConcurrentUtilities", "Dates", "ExceptionUnwrapping", "Logging", "LoggingExtras", "MbedTLS", "NetworkOptions", "OpenSSL", "PrecompileTools", "Random", "SimpleBufferStream", "Sockets", "URIs", "UUIDs"] +git-tree-sha1 = "c67b33b085f6e2faf8bf79a61962e7339a81129c" uuid = "cd3eb016-35fb-5094-929b-558a96fad6f3" -version = "1.10.9" +version = "1.10.15" [[deps.HarfBuzz_jll]] deps = ["Artifacts", "Cairo_jll", "Fontconfig_jll", "FreeType2_jll", "Glib_jll", "Graphite2_jll", "JLLWrappers", "Libdl", "Libffi_jll"] -git-tree-sha1 = "401e4f3f30f43af2c8478fc008da50096ea5240f" +git-tree-sha1 = "55c53be97790242c29031e5cd45e8ac296dadda3" uuid = "2e76f6c2-a576-52d4-95c1-20adfe4de566" -version = "8.3.1+0" +version = "8.5.0+0" [[deps.Hwloc_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "dd3b49277ec2bb2c6b94eb1604d4d0616016f7a6" +git-tree-sha1 = "f93a9ce66cd89c9ba7a4695a47fd93b4c6bc59fa" uuid = "e33a78d0-f292-5ffc-b300-72abe9b543c8" -version = "2.11.2+0" +version = "2.12.0+0" [[deps.HypergeometricFunctions]] deps = ["LinearAlgebra", "OpenLibm_jll", "SpecialFunctions"] -git-tree-sha1 = "7c4195be1649ae622304031ed46a2f4df989f1eb" +git-tree-sha1 = "68c173f4f449de5b438ee67ed0c9c748dc31a2ec" uuid = "34004b35-14d8-5ef3-9330-4cdb6864b03a" -version = "0.3.24" +version = "0.3.28" [[deps.Hyperscript]] deps = ["Test"] @@ -540,9 +548,9 @@ version = "0.0.5" [[deps.ImageAxes]] deps = ["AxisArrays", "ImageBase", "ImageCore", "Reexport", "SimpleTraits"] -git-tree-sha1 = "2e4520d67b0cef90865b3ef727594d2a58e0e1f8" +git-tree-sha1 = "e12629406c6c4442539436581041d372d69c55ba" uuid = "2803e5a7-5153-5ecf-9a86-9b4c37f5f5ac" -version = "0.6.11" +version = "0.6.12" [[deps.ImageBase]] deps = ["ImageCore", "Reexport"] @@ -552,9 +560,9 @@ version = "0.1.7" [[deps.ImageCore]] deps = ["ColorVectorSpace", "Colors", "FixedPointNumbers", "MappedArrays", "MosaicViews", "OffsetArrays", "PaddedViews", "PrecompileTools", "Reexport"] -git-tree-sha1 = "b2a7eaa169c13f5bcae8131a83bc30eff8f71be0" +git-tree-sha1 = "8c193230235bbcee22c8066b0374f63b5683c2d3" uuid = "a09fc81d-aa75-5fe9-8630-4744c3626534" -version = "0.10.2" +version = "0.10.5" [[deps.ImageIO]] deps = ["FileIO", "IndirectArrays", "JpegTurbo", "LazyModules", "Netpbm", "OpenEXR", "PNGFiles", "QOI", "Sixel", "TiffImages", "UUIDs", "WebP"] @@ -564,9 +572,9 @@ version = "0.6.9" [[deps.ImageMetadata]] deps = ["AxisArrays", "ImageAxes", "ImageBase", "ImageCore"] -git-tree-sha1 = "355e2b974f2e3212a75dfb60519de21361ad3cb7" +git-tree-sha1 = "2a81c3897be6fbcde0802a0ebe6796d0562f63ec" uuid = "bc367c6b-8a6b-528e-b4bd-a4b897500b49" -version = "0.9.9" +version = "0.9.10" [[deps.Imath_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] @@ -586,9 +594,9 @@ version = "0.1.5" [[deps.IntelOpenMP_jll]] deps = ["Artifacts", "JLLWrappers", "LazyArtifacts", "Libdl"] -git-tree-sha1 = "10bd689145d2c3b2a9844005d01087cc1194e79e" +git-tree-sha1 = "0f14a5456bdc6b9731a5682f439a672750a09e48" uuid = "1d5cc7b8-4909-519e-a0f8-d0f5ad9712d0" -version = "2024.2.1+0" +version = "2025.0.4+0" [[deps.InteractiveUtils]] deps = ["Markdown"] @@ -606,10 +614,10 @@ weakdeps = ["Unitful"] InterpolationsUnitfulExt = "Unitful" [[deps.IntervalArithmetic]] -deps = ["CRlibm_jll", "LinearAlgebra", "MacroTools", "RoundingEmulator"] -git-tree-sha1 = "24c095b1ec7ee58b936985d31d5df92f9b9cfebb" +deps = ["CRlibm_jll", "LinearAlgebra", "MacroTools", "OpenBLASConsistentFPCSR_jll", "RoundingEmulator"] +git-tree-sha1 = "dfbf101df925acf1caa3b15a00b574887cd8472d" uuid = "d1acc4aa-44c8-5952-acd4-ba5d80a2a253" -version = "0.22.19" +version = "0.22.26" [deps.IntervalArithmetic.extensions] IntervalArithmeticDiffRulesExt = "DiffRules" @@ -645,9 +653,9 @@ weakdeps = ["Dates", "Test"] InverseFunctionsTestExt = "Test" [[deps.IrrationalConstants]] -git-tree-sha1 = "630b497eafcc20001bba38a4651b327dcfc491d2" +git-tree-sha1 = "e2222959fbc6c19554dc15174c81bf7bf3aa691c" uuid = "92d709cd-6900-40b7-9082-c6be49f344b6" -version = "0.2.2" +version = "0.2.4" [[deps.Isoband]] deps = ["isoband_jll"] @@ -667,9 +675,9 @@ version = "1.0.0" [[deps.JLLWrappers]] deps = ["Artifacts", "Preferences"] -git-tree-sha1 = "be3dc50a92e5a386872a493a10050136d4703f9b" +git-tree-sha1 = "a007feb38b422fbdab534406aeca1b86823cb4d6" uuid = "692b3bcd-3c85-4b1f-b108-f13ce0eb3210" -version = "1.6.1" +version = "1.7.0" [[deps.JSON]] deps = ["Dates", "Mmap", "Parsers", "Unicode"] @@ -679,9 +687,9 @@ version = "0.21.4" [[deps.JSON3]] deps = ["Dates", "Mmap", "Parsers", "PrecompileTools", "StructTypes", "UUIDs"] -git-tree-sha1 = "1d322381ef7b087548321d3f878cb4c9bd8f8f9b" +git-tree-sha1 = "196b41e5a854b387d99e5ede2de3fcb4d0422aae" uuid = "0f8b85d8-7281-11e9-16c2-39a750bddbf1" -version = "1.14.1" +version = "1.14.2" [deps.JSON3.extensions] JSON3ArrowExt = ["ArrowTypes"] @@ -691,15 +699,15 @@ version = "1.14.1" [[deps.JpegTurbo]] deps = ["CEnum", "FileIO", "ImageCore", "JpegTurbo_jll", "TOML"] -git-tree-sha1 = "fa6d0bcff8583bac20f1ffa708c3913ca605c611" +git-tree-sha1 = "9496de8fb52c224a2e3f9ff403947674517317d9" uuid = "b835a17e-a41a-41e7-81f0-2f016b05efe0" -version = "0.1.5" +version = "0.1.6" [[deps.JpegTurbo_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "25ee0be4d43d0269027024d75a24c24d6c6e590c" +git-tree-sha1 = "eac1206917768cb54957c65a615460d87b455fc1" uuid = "aacddb02-875f-59d6-b918-886e6ef4fbf8" -version = "3.0.4+0" +version = "3.1.1+0" [[deps.KernelDensity]] deps = ["Distributions", "DocStringExtensions", "FFTW", "Interpolations", "StatsBase"] @@ -715,9 +723,9 @@ version = "3.100.2+0" [[deps.LERC_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "36bdbc52f13a7d1dcb0f3cd694e01677a515655b" +git-tree-sha1 = "aaafe88dccbd957a8d82f7d05be9b69172e0cee3" uuid = "88015f11-f218-50d7-93a8-a6af411a945d" -version = "4.0.0+0" +version = "4.0.1+0" [[deps.LLVMOpenMP_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] @@ -727,9 +735,9 @@ version = "18.1.7+0" [[deps.LZO_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "854a9c268c43b77b0a27f22d7fab8d33cdb3a731" +git-tree-sha1 = "1c602b1127f4751facb671441ca72715cc95938a" uuid = "dd4b983a-f0e5-5f8d-a1b7-129d4a5fb1ac" -version = "2.10.2+1" +version = "2.10.3+0" [[deps.LaTeXStrings]] git-tree-sha1 = "dda21b8cbd6a6c40d9d02a73230f9d70fed6918c" @@ -777,9 +785,9 @@ version = "1.11.0" [[deps.Libffi_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg"] -git-tree-sha1 = "0b4a5d71f3e5200a7dff793393e09dfc2d874290" +git-tree-sha1 = "27ecae93dd25ee0909666e6835051dd684cc035e" uuid = "e9f186c6-92d2-5b65-8a66-fee21dc1b490" -version = "3.2.2+1" +version = "3.2.2+2" [[deps.Libgcrypt_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Libgpg_error_jll"] @@ -788,40 +796,40 @@ uuid = "d4300ac3-e22c-5743-9152-c294e39db1e4" version = "1.11.0+0" [[deps.Libglvnd_jll]] -deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg", "Xorg_libX11_jll", "Xorg_libXext_jll"] -git-tree-sha1 = "6f73d1dd803986947b2c750138528a999a6c7733" +deps = ["Artifacts", "JLLWrappers", "Libdl", "Xorg_libX11_jll", "Xorg_libXext_jll"] +git-tree-sha1 = "ff3b4b9d35de638936a525ecd36e86a8bb919d11" uuid = "7e76a0d4-f3c7-5321-8279-8d96eeed0f29" -version = "1.6.0+0" +version = "1.7.0+0" [[deps.Libgpg_error_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "c6ce1e19f3aec9b59186bdf06cdf3c4fc5f5f3e6" +git-tree-sha1 = "df37206100d39f79b3376afb6b9cee4970041c61" uuid = "7add5ba3-2f88-524e-9cd5-f83b8a55f7b8" -version = "1.50.0+0" +version = "1.51.1+0" [[deps.Libiconv_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "61dfdba58e585066d8bce214c5a51eaa0539f269" +git-tree-sha1 = "be484f5c92fad0bd8acfef35fe017900b0b73809" uuid = "94ce4f54-9a6c-5748-9c1c-f9c7231a4531" -version = "1.17.0+1" +version = "1.18.0+0" [[deps.Libmount_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "0c4f9c4f1a50d8f35048fa0532dabbadf702f81e" +git-tree-sha1 = "89211ea35d9df5831fca5d33552c02bd33878419" uuid = "4b2f31a3-9ecc-558c-b454-b3730dcb73e9" -version = "2.40.1+0" +version = "2.40.3+0" [[deps.Libtiff_jll]] deps = ["Artifacts", "JLLWrappers", "JpegTurbo_jll", "LERC_jll", "Libdl", "XZ_jll", "Zlib_jll", "Zstd_jll"] -git-tree-sha1 = "b404131d06f7886402758c9ce2214b636eb4d54a" +git-tree-sha1 = "4ab7581296671007fc33f07a721631b8855f4b1d" uuid = "89763e89-9b03-5906-acba-b20f662cd828" -version = "4.7.0+0" +version = "4.7.1+0" [[deps.Libuuid_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "5ee6203157c120d79034c748a2acba45b82b8807" +git-tree-sha1 = "e888ad02ce716b319e6bdb985d2ef300e7089889" uuid = "38a345b3-de98-5d2b-a5d3-14cd9215e700" -version = "2.40.1+0" +version = "2.40.3+0" [[deps.LinearAlgebra]] deps = ["Libdl", "OpenBLAS_jll", "libblastrampoline_jll"] @@ -830,9 +838,9 @@ version = "1.11.0" [[deps.LogExpFunctions]] deps = ["DocStringExtensions", "IrrationalConstants", "LinearAlgebra"] -git-tree-sha1 = "a2d09619db4e765091ee5c6ffe8872849de0feea" +git-tree-sha1 = "13ca9e2586b89836fd20cccf56e57e2b9ae7f38f" uuid = "2ab3a3ac-af41-5b50-aa03-7779005ae688" -version = "0.3.28" +version = "0.3.29" [deps.LogExpFunctions.extensions] LogExpFunctionsChainRulesCoreExt = "ChainRulesCore" @@ -860,17 +868,22 @@ git-tree-sha1 = "1d2dd9b186742b0f317f2530ddcbf00eebb18e96" uuid = "23992714-dd62-5051-b70f-ba57cb901cac" version = "0.10.7" +[[deps.MIMEs]] +git-tree-sha1 = "c64d943587f7187e751162b3b84445bbbd79f691" +uuid = "6c6e2e6c-3030-632d-7369-2d6c69616d65" +version = "1.1.0" + [[deps.MKL_jll]] deps = ["Artifacts", "IntelOpenMP_jll", "JLLWrappers", "LazyArtifacts", "Libdl", "oneTBB_jll"] -git-tree-sha1 = "f046ccd0c6db2832a9f639e2c669c6fe867e5f4f" +git-tree-sha1 = "5de60bc6cb3899cd318d80d627560fae2e2d99ae" uuid = "856f044c-d86e-5d09-b602-aeab76dc8ba7" -version = "2024.2.0+0" +version = "2025.0.1+1" [[deps.MPICH_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "Hwloc_jll", "JLLWrappers", "LazyArtifacts", "Libdl", "MPIPreferences", "TOML"] -git-tree-sha1 = "7715e65c47ba3941c502bffb7f266a41a7f54423" +git-tree-sha1 = "3aa3210044138a1749dbd350a9ba8680869eb503" uuid = "7cb0a576-ebde-5e09-9194-50597f1243b4" -version = "4.2.3+0" +version = "4.3.0+1" [[deps.MPIPreferences]] deps = ["Libdl", "Preferences"] @@ -880,27 +893,26 @@ version = "0.1.11" [[deps.MPItrampoline_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "LazyArtifacts", "Libdl", "MPIPreferences", "TOML"] -git-tree-sha1 = "70e830dab5d0775183c99fc75e4c24c614ed7142" +git-tree-sha1 = "ff91ca13c7c472cef700f301c8d752bc2aaff1a8" uuid = "f1f71cc9-e9ae-5b93-9b94-4fe0e1ad3748" -version = "5.5.1+0" +version = "5.5.3+0" [[deps.MacroTools]] -deps = ["Markdown", "Random"] -git-tree-sha1 = "2fa9ee3e63fd3a4f7a9a4f4744a52f4856de82df" +git-tree-sha1 = "72aebe0b5051e5143a079a4685a46da330a40472" uuid = "1914dd2f-81c6-5fcd-8719-6d5c9610ff09" -version = "0.5.13" +version = "0.5.15" [[deps.Makie]] -deps = ["Animations", "Base64", "CRC32c", "ColorBrewer", "ColorSchemes", "ColorTypes", "Colors", "Contour", "Dates", "DelaunayTriangulation", "Distributions", "DocStringExtensions", "Downloads", "FFMPEG_jll", "FileIO", "FilePaths", "FixedPointNumbers", "Format", "FreeType", "FreeTypeAbstraction", "GeometryBasics", "GridLayoutBase", "ImageBase", "ImageIO", "InteractiveUtils", "Interpolations", "IntervalSets", "InverseFunctions", "Isoband", "KernelDensity", "LaTeXStrings", "LinearAlgebra", "MacroTools", "MakieCore", "Markdown", "MathTeXEngine", "Observables", "OffsetArrays", "Packing", "PlotUtils", "PolygonOps", "PrecompileTools", "Printf", "REPL", "Random", "RelocatableFolders", "Scratch", "ShaderAbstractions", "Showoff", "SignedDistanceFields", "SparseArrays", "Statistics", "StatsBase", "StatsFuns", "StructArrays", "TriplotBase", "UnicodeFun", "Unitful"] -git-tree-sha1 = "f7907907eb914138cc9e9ee66ab46f7a9efac8e8" +deps = ["Animations", "Base64", "CRC32c", "ColorBrewer", "ColorSchemes", "ColorTypes", "Colors", "Contour", "Dates", "DelaunayTriangulation", "Distributions", "DocStringExtensions", "Downloads", "FFMPEG_jll", "FileIO", "FilePaths", "FixedPointNumbers", "Format", "FreeType", "FreeTypeAbstraction", "GeometryBasics", "GridLayoutBase", "ImageBase", "ImageIO", "InteractiveUtils", "Interpolations", "IntervalSets", "InverseFunctions", "Isoband", "KernelDensity", "LaTeXStrings", "LinearAlgebra", "MacroTools", "MakieCore", "Markdown", "MathTeXEngine", "Observables", "OffsetArrays", "PNGFiles", "Packing", "PlotUtils", "PolygonOps", "PrecompileTools", "Printf", "REPL", "Random", "RelocatableFolders", "Scratch", "ShaderAbstractions", "Showoff", "SignedDistanceFields", "SparseArrays", "Statistics", "StatsBase", "StatsFuns", "StructArrays", "TriplotBase", "UnicodeFun", "Unitful"] +git-tree-sha1 = "e64b545d25e05a609521bfc36724baa072bfd31a" uuid = "ee78f7c6-11fb-53f2-987a-cfe4a2b5a57a" -version = "0.21.15" +version = "0.22.2" [[deps.MakieCore]] deps = ["ColorTypes", "GeometryBasics", "IntervalSets", "Observables"] -git-tree-sha1 = "4604f03e5b057e8e62a95a44929cafc9585b0fe9" +git-tree-sha1 = "605d6e8f2b7eba7f5bc6a16d297475075d5ea775" uuid = "20f20a25-4f0e-4fdf-b5d1-57303727442b" -version = "0.8.9" +version = "0.9.1" [[deps.MappedArrays]] git-tree-sha1 = "2dab0221fe2b0f2cb6754eaa743cc266339f527e" @@ -937,9 +949,9 @@ version = "0.29.0" [[deps.MicrosoftMPI_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg"] -git-tree-sha1 = "f12a29c4400ba812841c6ace3f4efbb6dbb3ba01" +git-tree-sha1 = "bc95bf4149bf535c09602e3acdf950d9b4376227" uuid = "9237b28f-5490-5468-be7b-bb81f5f5e6cf" -version = "10.1.4+2" +version = "10.1.4+3" [[deps.Missings]] deps = ["DataAPI"] @@ -969,9 +981,9 @@ version = "1.2.1" [[deps.NearestNeighbors]] deps = ["Distances", "StaticArrays"] -git-tree-sha1 = "3cebfc94a0754cc329ebc3bab1e6c89621e791ad" +git-tree-sha1 = "8a3271d8309285f4db73b4f662b1b290c715e85e" uuid = "b8a86587-4115-5ab1-83bc-aa920d37bbce" -version = "0.4.20" +version = "0.4.21" [[deps.Netpbm]] deps = ["FileIO", "ImageCore", "ImageMetadata"] @@ -985,11 +997,11 @@ version = "1.2.0" [[deps.NyxWidgets]] deps = ["Bonito", "Colors", "Format", "LazyArtifacts", "Observables"] -git-tree-sha1 = "e18ab14817871c54419e4cef12f9fc4dc589f6fe" +git-tree-sha1 = "d5addf940e4265b3ca2a6fe29b8ff24bf3b13b98" repo-rev = "main" repo-url = "https://gitlab.com/dbc-nyx/NyxWidgets.jl" uuid = "c288fd06-43d3-4b04-8307-797133353e2e" -version = "0.2.0" +version = "0.2.1" [[deps.Observables]] git-tree-sha1 = "7438a59546cf62428fc9d1bc94729146d37a7225" @@ -1005,9 +1017,9 @@ uuid = "6317928a-6b1a-42e8-b853-b8e2fc3e9ca3" version = "0.2.4" [[deps.OffsetArrays]] -git-tree-sha1 = "1a27764e945a152f7ca7efa04de513d473e9542e" +git-tree-sha1 = "a414039192a155fb38c4599a60110f0018c6ec82" uuid = "6fe1bfb0-de20-5000-8ca7-80f57d26f881" -version = "1.14.1" +version = "1.16.0" weakdeps = ["Adapt"] [deps.OffsetArrays.extensions] @@ -1019,6 +1031,12 @@ git-tree-sha1 = "887579a3eb005446d514ab7aeac5d1d027658b8f" uuid = "e7412a2a-1a6e-54c0-be00-318e2571c051" version = "1.3.5+1" +[[deps.OpenBLASConsistentFPCSR_jll]] +deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "Libdl"] +git-tree-sha1 = "567515ca155d0020a45b05175449b499c63e7015" +uuid = "6cdc7f73-28fd-5e50-80fb-958a8875b1af" +version = "0.3.29+0" + [[deps.OpenBLAS_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "Libdl"] uuid = "4536629a-c528-5b80-bd46-f80d51c5b363" @@ -1026,9 +1044,9 @@ version = "0.3.27+1" [[deps.OpenEXR]] deps = ["Colors", "FileIO", "OpenEXR_jll"] -git-tree-sha1 = "327f53360fdb54df7ecd01e96ef1983536d1e633" +git-tree-sha1 = "97db9e07fe2091882c765380ef58ec553074e9c7" uuid = "52e1d378-f018-4a11-a4be-720524705ac7" -version = "0.3.2" +version = "0.3.3" [[deps.OpenEXR_jll]] deps = ["Artifacts", "Imath_jll", "JLLWrappers", "Libdl", "Zlib_jll"] @@ -1039,13 +1057,13 @@ version = "3.2.4+0" [[deps.OpenLibm_jll]] deps = ["Artifacts", "Libdl"] uuid = "05823500-19ac-5b8b-9628-191a04bc5112" -version = "0.8.1+2" +version = "0.8.1+4" [[deps.OpenMPI_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "Hwloc_jll", "JLLWrappers", "LazyArtifacts", "Libdl", "MPIPreferences", "TOML", "Zlib_jll"] -git-tree-sha1 = "bfce6d523861a6c562721b262c0d1aaeead2647f" +git-tree-sha1 = "da913f03f17b449951e0461da960229d4a3d1a8c" uuid = "fe0851c0-eecd-5654-98d4-656369965a5c" -version = "5.0.5+0" +version = "5.0.7+1" [[deps.OpenSSL]] deps = ["BitFlags", "Dates", "MozillaCACerts_jll", "OpenSSL_jll", "Sockets"] @@ -1055,15 +1073,15 @@ version = "1.4.3" [[deps.OpenSSL_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "7493f61f55a6cce7325f197443aa80d32554ba10" +git-tree-sha1 = "a9697f1d06cc3eb3fb3ad49cc67f2cfabaac31ea" uuid = "458c3c95-2e84-50aa-8efc-19380b2a3a95" -version = "3.0.15+1" +version = "3.0.16+0" [[deps.OpenSpecFun_jll]] -deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "Libdl", "Pkg"] -git-tree-sha1 = "13652491f6856acfd2db29360e1bbcd4565d04f1" +deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "Libdl"] +git-tree-sha1 = "1346c9208249809840c91b26703912dff463d335" uuid = "efe28fd5-8261-553b-a9e1-b2916fc3738e" -version = "0.5.5+0" +version = "0.5.6+0" [[deps.Opus_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] @@ -1072,9 +1090,15 @@ uuid = "91d4177d-7536-5919-b921-800302f37372" version = "1.3.3+0" [[deps.OrderedCollections]] -git-tree-sha1 = "dfdf5519f235516220579f949664f1bf44e741c5" +git-tree-sha1 = "cc4054e898b852042d7b503313f7ad03de99c3dd" uuid = "bac558e1-5e72-5ebc-8fee-abe8a469f55d" -version = "1.6.3" +version = "1.8.0" + +[[deps.Oxygen]] +deps = ["DataStructures", "Dates", "HTTP", "JSON3", "MIMEs", "Reexport", "RelocatableFolders", "Requires", "Sockets", "Statistics", "StructTypes"] +git-tree-sha1 = "2ad010b0de6172faf1d09ed5e0837eb0b7355bd8" +uuid = "df9a0d86-3283-4920-82dc-4555fc0d1d8b" +version = "1.5.16" [[deps.PCRE2_jll]] deps = ["Artifacts", "Libdl"] @@ -1083,21 +1107,21 @@ version = "10.42.0+1" [[deps.PDMats]] deps = ["LinearAlgebra", "SparseArrays", "SuiteSparse"] -git-tree-sha1 = "949347156c25054de2db3b166c52ac4728cbad65" +git-tree-sha1 = "48566789a6d5f6492688279e22445002d171cf76" uuid = "90014a1f-27ba-587c-ab20-58faa44d9150" -version = "0.11.31" +version = "0.11.33" [[deps.PNGFiles]] deps = ["Base64", "CEnum", "ImageCore", "IndirectArrays", "OffsetArrays", "libpng_jll"] -git-tree-sha1 = "67186a2bc9a90f9f85ff3cc8277868961fb57cbd" +git-tree-sha1 = "cf181f0b1e6a18dfeb0ee8acc4a9d1672499626c" uuid = "f57f5aa1-a3ce-4bc8-8ab9-96f992907883" -version = "0.4.3" +version = "0.4.4" [[deps.Packing]] deps = ["GeometryBasics"] -git-tree-sha1 = "ec3edfe723df33528e085e632414499f26650501" +git-tree-sha1 = "bc5bf2ea3d5351edf285a06b0016788a121ce92c" uuid = "19eb6ba3-879d-56ad-ad62-d5c202156566" -version = "0.5.0" +version = "0.5.1" [[deps.PaddedViews]] deps = ["OffsetArrays"] @@ -1113,9 +1137,9 @@ version = "2.8.1" [[deps.Pixman_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "LLVMOpenMP_jll", "Libdl"] -git-tree-sha1 = "35621f10a7531bc8fa58f74610b1bfb70a3cfc6b" +git-tree-sha1 = "db76b1ecd5e9715f3d043cec13b2ec93ce015d53" uuid = "30392449-352a-5448-841d-b1acce4e97dc" -version = "0.43.4+0" +version = "0.44.2+0" [[deps.Pkg]] deps = ["Artifacts", "Dates", "Downloads", "FileWatching", "LibGit2", "Libdl", "Logging", "Markdown", "Printf", "Random", "SHA", "TOML", "Tar", "UUIDs", "p7zip_jll"] @@ -1136,7 +1160,7 @@ version = "0.3.3" deps = ["DelimitedFiles", "HDF5", "JSON3", "LinearAlgebra", "MAT", "Meshes", "OrderedCollections", "Random", "SHA", "StaticArrays", "Statistics", "StatsBase", "StructTypes"] git-tree-sha1 = "d964d040e319fe3bd9140e5bf91d648de6acc96f" repo-rev = "main" -repo-url = "https://gitlab.pasteur.fr/nyx/planarlarvae.jl" +repo-url = "https://gitlab.pasteur.fr/nyx/PlanarLarvae.jl" uuid = "c2615984-ef14-4d40-b148-916c85b43307" version = "0.16.0" @@ -1175,21 +1199,21 @@ uuid = "92933f4c-e287-5a05-a399-4b506db050ca" version = "1.10.2" [[deps.PtrArrays]] -git-tree-sha1 = "77a42d78b6a92df47ab37e177b2deac405e1c88f" +git-tree-sha1 = "1d36ef11a9aaf1e8b74dacc6a731dd1de8fd493d" uuid = "43287f4e-b6f4-7ad1-bb20-aadabca52c3d" -version = "1.2.1" +version = "1.3.0" [[deps.QOI]] deps = ["ColorTypes", "FileIO", "FixedPointNumbers"] -git-tree-sha1 = "18e8f4d1426e965c7b532ddd260599e1510d26ce" +git-tree-sha1 = "8b3fc30bc0390abdce15f8822c889f669baed73d" uuid = "4b34888f-f399-49d4-9bb3-47ed5cae4e65" -version = "1.0.0" +version = "1.0.1" [[deps.QuadGK]] deps = ["DataStructures", "LinearAlgebra"] -git-tree-sha1 = "cda3b045cf9ef07a08ad46731f5a3165e56cf3da" +git-tree-sha1 = "9da16da70037ba9d701192e27befedefb91ec284" uuid = "1fd47b50-473d-5c70-9696-f719f8f3bcdc" -version = "2.11.1" +version = "2.11.2" [deps.QuadGK.extensions] QuadGKEnzymeExt = "Enzyme" @@ -1253,9 +1277,9 @@ version = "1.0.1" [[deps.Requires]] deps = ["UUIDs"] -git-tree-sha1 = "838a3a4188e2ded87a4f9f184b4b0d78a1e91cb7" +git-tree-sha1 = "62389eeff14780bfe55195b7204c0d8738436d64" uuid = "ae029012-a4dd-5104-9daa-d747884805df" -version = "1.3.0" +version = "1.3.1" [[deps.Rmath]] deps = ["Random", "Rmath_jll"] @@ -1290,9 +1314,9 @@ version = "0.7.0" [[deps.SIMD]] deps = ["PrecompileTools"] -git-tree-sha1 = "98ca7c29edd6fc79cd74c61accb7010a4e7aee33" +git-tree-sha1 = "fea870727142270bdf7624ad675901a1ee3b4c87" uuid = "fdea26ae-647d-5447-a871-4b548cad5224" -version = "3.6.0" +version = "3.7.1" [[deps.Scratch]] deps = ["Dates"] @@ -1305,10 +1329,10 @@ uuid = "9e88b42a-f829-5b0c-bbe9-9e923198166b" version = "1.11.0" [[deps.ShaderAbstractions]] -deps = ["ColorTypes", "FixedPointNumbers", "GeometryBasics", "LinearAlgebra", "Observables", "StaticArrays", "StructArrays", "Tables"] -git-tree-sha1 = "79123bc60c5507f035e6d1d9e563bb2971954ec8" +deps = ["ColorTypes", "FixedPointNumbers", "GeometryBasics", "LinearAlgebra", "Observables", "StaticArrays"] +git-tree-sha1 = "818554664a2e01fc3784becb2eb3a82326a604b6" uuid = "65257c39-d410-5151-9873-9b3e5be5013e" -version = "0.4.1" +version = "0.5.0" [[deps.SharedArrays]] deps = ["Distributed", "Mmap", "Random", "Serialization"] @@ -1361,9 +1385,9 @@ version = "1.11.0" [[deps.SpecialFunctions]] deps = ["IrrationalConstants", "LogExpFunctions", "OpenLibm_jll", "OpenSpecFun_jll"] -git-tree-sha1 = "2f5d4697f21388cbe1ff299430dd169ef97d7e14" +git-tree-sha1 = "64cca0c26b4f31ba18f13f6c12af7c85f478cfde" uuid = "276daf66-3868-5448-9aa4-cd146d93841b" -version = "2.4.0" +version = "2.5.0" weakdeps = ["ChainRulesCore"] [deps.SpecialFunctions.extensions] @@ -1383,9 +1407,9 @@ version = "0.1.1" [[deps.StaticArrays]] deps = ["LinearAlgebra", "PrecompileTools", "Random", "StaticArraysCore"] -git-tree-sha1 = "777657803913ffc7e8cc20f0fd04b634f871af8f" +git-tree-sha1 = "0feb6b9031bd5c51f9072393eb5ab3efd31bf9e4" uuid = "90137ffa-7385-5640-81b9-e52037218182" -version = "1.9.8" +version = "1.9.13" weakdeps = ["ChainRulesCore", "Statistics"] [deps.StaticArrays.extensions] @@ -1414,10 +1438,10 @@ uuid = "82ae8749-77ed-4fe6-ae5f-f523153014b0" version = "1.7.0" [[deps.StatsBase]] -deps = ["DataAPI", "DataStructures", "LinearAlgebra", "LogExpFunctions", "Missings", "Printf", "Random", "SortingAlgorithms", "SparseArrays", "Statistics", "StatsAPI"] -git-tree-sha1 = "5cf7606d6cef84b543b483848d4ae08ad9832b21" +deps = ["AliasTables", "DataAPI", "DataStructures", "LinearAlgebra", "LogExpFunctions", "Missings", "Printf", "Random", "SortingAlgorithms", "SparseArrays", "Statistics", "StatsAPI"] +git-tree-sha1 = "29321314c920c26684834965ec2ce0dacc9cf8e5" uuid = "2913bbd2-ae8a-5f71-8c99-4fb6c76f3a91" -version = "0.34.3" +version = "0.34.4" [[deps.StatsFuns]] deps = ["HypergeometricFunctions", "IrrationalConstants", "LogExpFunctions", "Reexport", "Rmath", "SpecialFunctions"] @@ -1432,19 +1456,22 @@ weakdeps = ["ChainRulesCore", "InverseFunctions"] [[deps.StructArrays]] deps = ["ConstructionBase", "DataAPI", "Tables"] -git-tree-sha1 = "f4dc295e983502292c4c3f951dbb4e985e35b3be" +git-tree-sha1 = "5a3a31c41e15a1e042d60f2f4942adccba05d3c9" uuid = "09ab397b-f2b6-538f-b94a-2f83cf4a842a" -version = "0.6.18" +version = "0.7.0" [deps.StructArrays.extensions] StructArraysAdaptExt = "Adapt" - StructArraysGPUArraysCoreExt = "GPUArraysCore" + StructArraysGPUArraysCoreExt = ["GPUArraysCore", "KernelAbstractions"] + StructArraysLinearAlgebraExt = "LinearAlgebra" StructArraysSparseArraysExt = "SparseArrays" StructArraysStaticArraysExt = "StaticArrays" [deps.StructArrays.weakdeps] Adapt = "79e6a3ab-5dfb-504d-930d-738a2a938a0e" GPUArraysCore = "46192b85-c4d5-4398-a991-12ede77f4527" + KernelAbstractions = "63c18a36-062a-441e-b654-da1e3ab1ce7c" + LinearAlgebra = "37e2e46d-f89d-539d-b4ee-838fcccc9c8e" SparseArrays = "2f01184e-e22b-5df5-ae63-d93ebab69eaf" StaticArrays = "90137ffa-7385-5640-81b9-e52037218182" @@ -1510,15 +1537,15 @@ version = "2.1.1" deps = ["Observables"] git-tree-sha1 = "0589ec7397374678942cae9aa356b4bb6c1e9bf4" repo-rev = "main" -repo-url = "https://gitlab.com/dbc-nyx/tidyobservables.jl" +repo-url = "https://gitlab.com/dbc-nyx/TidyObservables.jl" uuid = "c8131bbd-73a8-4254-a42d-d5d4c5febb31" version = "0.1.1" [[deps.TiffImages]] deps = ["ColorTypes", "DataStructures", "DocStringExtensions", "FileIO", "FixedPointNumbers", "IndirectArrays", "Inflate", "Mmap", "OffsetArrays", "PkgVersion", "ProgressMeter", "SIMD", "UUIDs"] -git-tree-sha1 = "6ee0c220d0aecad18792c277ae358129cc50a475" +git-tree-sha1 = "f21231b166166bebc73b99cea236071eb047525b" uuid = "731e570b-9d59-4bfa-96dc-6df516fadf69" -version = "0.11.0" +version = "0.11.3" [[deps.TranscodingStreams]] git-tree-sha1 = "0c45878dcfdcfa8480052b6ab162cdd138781742" @@ -1537,9 +1564,9 @@ uuid = "981d1d27-644d-49a2-9326-4793e63143c3" version = "0.1.0" [[deps.URIs]] -git-tree-sha1 = "67db6cc7b3821e19ebe75791a9dd19c9b1188f2b" +git-tree-sha1 = "cbbebadbcc76c5ca1cc4b4f3b0614b3e603b5000" uuid = "5c2747f8-b7ea-4ff2-ba2e-563bfd36b1d4" -version = "1.5.1" +version = "1.5.2" [[deps.UUIDs]] deps = ["Random", "SHA"] @@ -1558,9 +1585,9 @@ version = "0.4.1" [[deps.Unitful]] deps = ["Dates", "LinearAlgebra", "Random"] -git-tree-sha1 = "d95fe458f26209c66a187b1114df96fd70839efd" +git-tree-sha1 = "c0667a8e676c53d390a09dc6870b3d8d6650e2bf" uuid = "1986cc42-f94f-5a68-af5c-568840ba703d" -version = "1.21.0" +version = "1.22.0" weakdeps = ["ConstructionBase", "InverseFunctions"] [deps.Unitful.extensions] @@ -1569,15 +1596,15 @@ weakdeps = ["ConstructionBase", "InverseFunctions"] [[deps.WGLMakie]] deps = ["Bonito", "Colors", "FileIO", "FreeTypeAbstraction", "GeometryBasics", "Hyperscript", "LinearAlgebra", "Makie", "Observables", "PNGFiles", "PrecompileTools", "RelocatableFolders", "ShaderAbstractions", "StaticArrays"] -git-tree-sha1 = "13cab94d885d7760d487d7e2f30c2d6df4643880" +git-tree-sha1 = "94de96cef3e4b9ec09096f6e5e9814041d59300c" uuid = "276b4fcb-3e11-5398-bf8b-a0c2d153d008" -version = "0.10.15" +version = "0.11.2" [[deps.WebP]] deps = ["CEnum", "ColorTypes", "FileIO", "FixedPointNumbers", "ImageCore", "libwebp_jll"] -git-tree-sha1 = "f1f6d497ff84039deeb37f264396dac0c2250497" +git-tree-sha1 = "aa1ca3c47f119fbdae8770c29820e5e6119b83f2" uuid = "e3aaa7dc-3e4b-44e0-be63-ffb868ccd7c1" -version = "0.1.2" +version = "0.1.3" [[deps.WidgetsBase]] deps = ["Observables"] @@ -1593,69 +1620,69 @@ version = "1.0.0" [[deps.XML2_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Libiconv_jll", "Zlib_jll"] -git-tree-sha1 = "6a451c6f33a176150f315726eba8b92fbfdb9ae7" +git-tree-sha1 = "b8b243e47228b4a3877f1dd6aee0c5d56db7fcf4" uuid = "02c8fc9c-b97f-50b9-bbe4-9be30ff0a78a" -version = "2.13.4+0" +version = "2.13.6+1" [[deps.XSLT_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Libgcrypt_jll", "Libgpg_error_jll", "Libiconv_jll", "XML2_jll", "Zlib_jll"] -git-tree-sha1 = "a54ee957f4c86b526460a720dbc882fa5edcbefc" +git-tree-sha1 = "7d1671acbe47ac88e981868a078bd6b4e27c5191" uuid = "aed1982a-8fda-507f-9586-7b0439959a61" -version = "1.1.41+0" +version = "1.1.42+0" [[deps.XZ_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "15e637a697345f6743674f1322beefbc5dcd5cfc" +git-tree-sha1 = "56c6604ec8b2d82cc4cfe01aa03b00426aac7e1f" uuid = "ffd25f8a-64ca-5728-b0f7-c24cf3aae800" -version = "5.6.3+0" +version = "5.6.4+1" [[deps.Xorg_libX11_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Xorg_libxcb_jll", "Xorg_xtrans_jll"] -git-tree-sha1 = "afead5aba5aa507ad5a3bf01f58f82c8d1403495" +git-tree-sha1 = "9dafcee1d24c4f024e7edc92603cedba72118283" uuid = "4f6342f7-b3d2-589e-9d20-edeb45f2b2bc" -version = "1.8.6+0" +version = "1.8.6+3" [[deps.Xorg_libXau_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "6035850dcc70518ca32f012e46015b9beeda49d8" +git-tree-sha1 = "e9216fdcd8514b7072b43653874fd688e4c6c003" uuid = "0c0b7dd1-d40b-584c-a123-a41640f87eec" -version = "1.0.11+0" +version = "1.0.12+0" [[deps.Xorg_libXdmcp_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "34d526d318358a859d7de23da945578e8e8727b7" +git-tree-sha1 = "89799ae67c17caa5b3b5a19b8469eeee474377db" uuid = "a3789734-cfe1-5b06-b2d0-1dd0d9d62d05" -version = "1.1.4+0" +version = "1.1.5+0" [[deps.Xorg_libXext_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Xorg_libX11_jll"] -git-tree-sha1 = "d2d1a5c49fae4ba39983f63de6afcbea47194e85" +git-tree-sha1 = "d7155fea91a4123ef59f42c4afb5ab3b4ca95058" uuid = "1082639a-0dae-5f34-9b06-72781eeb8cb3" -version = "1.3.6+0" +version = "1.3.6+3" [[deps.Xorg_libXrender_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Xorg_libX11_jll"] -git-tree-sha1 = "47e45cd78224c53109495b3e324df0c37bb61fbe" +git-tree-sha1 = "a490c6212a0e90d2d55111ac956f7c4fa9c277a6" uuid = "ea2f1a96-1ddc-540d-b46f-429655e07cfa" -version = "0.9.11+0" +version = "0.9.11+1" [[deps.Xorg_libpthread_stubs_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "8fdda4c692503d44d04a0603d9ac0982054635f9" +git-tree-sha1 = "c57201109a9e4c0585b208bb408bc41d205ac4e9" uuid = "14d82f49-176c-5ed1-bb49-ad3f5cbd8c74" -version = "0.1.1+0" +version = "0.1.2+0" [[deps.Xorg_libxcb_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "XSLT_jll", "Xorg_libXau_jll", "Xorg_libXdmcp_jll", "Xorg_libpthread_stubs_jll"] -git-tree-sha1 = "bcd466676fef0878338c61e655629fa7bbc69d8e" +git-tree-sha1 = "1a74296303b6524a0472a8cb12d3d87a78eb3612" uuid = "c7cfdc94-dc32-55de-ac96-5a1b8d977c5b" -version = "1.17.0+0" +version = "1.17.0+3" [[deps.Xorg_xtrans_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "e92a1a012a10506618f10b7047e478403a046c77" +git-tree-sha1 = "6dba04dbfb72ae3ebe5418ba33d087ba8aa8cb00" uuid = "c5fb5394-a638-5e4d-96e5-b29de1b5cf10" -version = "1.5.0+0" +version = "1.5.1+0" [[deps.Zlib_jll]] deps = ["Libdl"] @@ -1664,9 +1691,9 @@ version = "1.2.13+1" [[deps.Zstd_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "555d1076590a6cc2fdee2ef1469451f872d8b41b" +git-tree-sha1 = "446b23e73536f84e8037f5dce465e92275f6a308" uuid = "3161d3a3-bdf6-5164-811a-617609db77b4" -version = "1.5.6+1" +version = "1.5.7+1" [[deps.isoband_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg"] @@ -1676,15 +1703,15 @@ version = "0.2.3+0" [[deps.libaec_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "46bf7be2917b59b761247be3f317ddf75e50e997" +git-tree-sha1 = "f5733a5a9047722470b95a81e1b172383971105c" uuid = "477f73a3-ac25-53e9-8cc3-50b2fa2566f0" -version = "1.1.2+0" +version = "1.1.3+0" [[deps.libaom_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "1827acba325fdcdf1d2647fc8d5301dd9ba43a9d" +git-tree-sha1 = "522c1df09d05a71785765d19c9524661234738e9" uuid = "a4ae2306-e953-59d6-aa16-d00cac43593b" -version = "3.9.0+0" +version = "3.11.0+0" [[deps.libass_jll]] deps = ["Artifacts", "Bzip2_jll", "FreeType2_jll", "FriBidi_jll", "HarfBuzz_jll", "JLLWrappers", "Libdl", "Zlib_jll"] @@ -1705,15 +1732,15 @@ version = "2.0.3+0" [[deps.libpng_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Zlib_jll"] -git-tree-sha1 = "b70c870239dc3d7bc094eb2d6be9b73d27bef280" +git-tree-sha1 = "068dfe202b0a05b8332f1e8e6b4080684b9c7700" uuid = "b53b4c65-9356-5827-b1ea-8c7a1a84506f" -version = "1.6.44+0" +version = "1.6.47+0" [[deps.libsixel_jll]] -deps = ["Artifacts", "JLLWrappers", "JpegTurbo_jll", "Libdl", "Pkg", "libpng_jll"] -git-tree-sha1 = "7dfa0fd9c783d3d0cc43ea1af53d69ba45c447df" +deps = ["Artifacts", "JLLWrappers", "JpegTurbo_jll", "Libdl", "libpng_jll"] +git-tree-sha1 = "c1733e347283df07689d71d61e14be986e49e47a" uuid = "075b6546-f08a-558a-be8f-8157d0f608a5" -version = "1.10.3+1" +version = "1.10.5+0" [[deps.libvorbis_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Ogg_jll", "Pkg"] @@ -1723,9 +1750,9 @@ version = "1.3.7+2" [[deps.libwebp_jll]] deps = ["Artifacts", "Giflib_jll", "JLLWrappers", "JpegTurbo_jll", "Libdl", "Libglvnd_jll", "Libtiff_jll", "libpng_jll"] -git-tree-sha1 = "ccbb625a89ec6195856a50aa2b668a5c08712c94" +git-tree-sha1 = "d2408cac540942921e7bd77272c32e58c33d8a77" uuid = "c5f90fcd-3b7e-5836-afba-fc50a0988cb2" -version = "1.4.0+0" +version = "1.5.0+0" [[deps.nghttp2_jll]] deps = ["Artifacts", "Libdl"] @@ -1734,9 +1761,9 @@ version = "1.59.0+0" [[deps.oneTBB_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "7d0ea0f4895ef2f5cb83645fa689e52cb55cf493" +git-tree-sha1 = "d5a767a3bb77135a99e433afe0eb14cd7f6914c3" uuid = "1317d2d5-d96f-522e-a858-c73665f53c3e" -version = "2021.12.0+0" +version = "2022.0.0+0" [[deps.p7zip_jll]] deps = ["Artifacts", "Libdl"] @@ -1745,9 +1772,9 @@ version = "17.4.0+2" [[deps.x264_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "35976a1216d6c066ea32cba2150c4fa682b276fc" +git-tree-sha1 = "14cc7083fc6dff3cc44f2bc435ee96d06ed79aa7" uuid = "1270edf5-f2f9-52d2-97e9-ab00b5d0237a" -version = "10164.0.0+0" +version = "10164.0.1+0" [[deps.x265_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] diff --git a/Manifest.toml b/Manifest.toml index af56fc6..5b90db9 100644 --- a/Manifest.toml +++ b/Manifest.toml @@ -22,12 +22,13 @@ version = "0.4.5" [[deps.Adapt]] deps = ["LinearAlgebra", "Requires"] -git-tree-sha1 = "50c3c56a52972d78e8be9fd135bfb91c9574c140" +git-tree-sha1 = "f7817e2e585aa6d924fd714df1e2a84be7896c60" uuid = "79e6a3ab-5dfb-504d-930d-738a2a938a0e" -version = "4.1.1" -weakdeps = ["StaticArrays"] +version = "4.3.0" +weakdeps = ["SparseArrays", "StaticArrays"] [deps.Adapt.extensions] + AdaptSparseArraysExt = "SparseArrays" AdaptStaticArraysExt = "StaticArrays" [[deps.AdaptivePredicates]] @@ -43,9 +44,9 @@ version = "1.1.3" [[deps.Animations]] deps = ["Colors"] -git-tree-sha1 = "e81c509d2c8e49592413bfb0bb3b08150056c79d" +git-tree-sha1 = "e092fa223bf66a3c41f9c022bd074d916dc303e7" uuid = "27a7e980-b3e6-11e9-2bcd-0b925532e340" -version = "0.4.1" +version = "0.4.2" [[deps.ArgTools]] uuid = "0dad84c5-d112-42e6-8d28-ef12dabb789f" @@ -97,10 +98,10 @@ uuid = "e1450e63-4bb3-523b-b2a4-4ffa8c0fd77d" version = "1.2.2" [[deps.Bzip2_jll]] -deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg"] -git-tree-sha1 = "8873e196c2eb87962a2048b3b8e08946535864a1" +deps = ["Artifacts", "JLLWrappers", "Libdl"] +git-tree-sha1 = "1b96ea4a01afe0ea4090c5c8039690672dd13f2e" uuid = "6e34b625-4abd-537c-b88f-471c36dfa7a0" -version = "1.0.8+2" +version = "1.0.9+0" [[deps.CEnum]] git-tree-sha1 = "389ad5c84de1ae7cf0e28e381131c98ea87d54fc" @@ -118,15 +119,15 @@ version = "1.0.1+0" [[deps.Cairo_jll]] deps = ["Artifacts", "Bzip2_jll", "CompilerSupportLibraries_jll", "Fontconfig_jll", "FreeType2_jll", "Glib_jll", "JLLWrappers", "LZO_jll", "Libdl", "Pixman_jll", "Xorg_libXext_jll", "Xorg_libXrender_jll", "Zlib_jll", "libpng_jll"] -git-tree-sha1 = "009060c9a6168704143100f36ab08f06c2af4642" +git-tree-sha1 = "2ac646d71d0d24b44f3f8c84da8c9f4d70fb67df" uuid = "83423d85-b0ee-5818-9007-b63ccbeb887a" -version = "1.18.2+1" +version = "1.18.4+0" [[deps.ChainRulesCore]] deps = ["Compat", "LinearAlgebra"] -git-tree-sha1 = "3e4b134270b372f2ed4d4d0e936aabaefc1802bc" +git-tree-sha1 = "1713c74e00545bfe14605d2a2be1712de8fbcb58" uuid = "d360d2e6-b24c-11e9-a2a3-2a2ae2dbcce4" -version = "1.25.0" +version = "1.25.1" weakdeps = ["SparseArrays"] [deps.ChainRulesCore.extensions] @@ -140,33 +141,39 @@ version = "1.4.0" [[deps.CodecZlib]] deps = ["TranscodingStreams", "Zlib_jll"] -git-tree-sha1 = "bce6804e5e6044c6daab27bb533d1295e4a2e759" +git-tree-sha1 = "962834c22b66e32aa10f7611c08c8ca4e20749a9" uuid = "944b1d66-785c-5afd-91f1-9de20f533193" -version = "0.7.6" +version = "0.7.8" [[deps.ColorBrewer]] -deps = ["Colors", "JSON", "Test"] -git-tree-sha1 = "61c5334f33d91e570e1d0c3eb5465835242582c4" +deps = ["Colors", "JSON"] +git-tree-sha1 = "e771a63cc8b539eca78c85b0cabd9233d6c8f06f" uuid = "a2cac450-b92f-5266-8821-25eda20663c8" -version = "0.4.0" +version = "0.4.1" [[deps.ColorSchemes]] deps = ["ColorTypes", "ColorVectorSpace", "Colors", "FixedPointNumbers", "PrecompileTools", "Random"] -git-tree-sha1 = "c785dfb1b3bfddd1da557e861b919819b82bbe5b" +git-tree-sha1 = "403f2d8e209681fcbd9468a8514efff3ea08452e" uuid = "35d6a980-a343-548e-a6ea-1d62b119f2f4" -version = "3.27.1" +version = "3.29.0" [[deps.ColorTypes]] deps = ["FixedPointNumbers", "Random"] -git-tree-sha1 = "b10d0b65641d57b8b4d5e234446582de5047050d" +git-tree-sha1 = "c7acce7a7e1078a20a285211dd73cd3941a871d6" uuid = "3da002f7-5984-5a60-b8a6-cbb66c0b333f" -version = "0.11.5" +version = "0.12.0" + + [deps.ColorTypes.extensions] + StyledStringsExt = "StyledStrings" + + [deps.ColorTypes.weakdeps] + StyledStrings = "f489334b-da3d-4c2e-b8f0-e476e12c162b" [[deps.ColorVectorSpace]] deps = ["ColorTypes", "FixedPointNumbers", "LinearAlgebra", "Requires", "Statistics", "TensorCore"] -git-tree-sha1 = "a1f44953f2382ebb937d60dafbe2deea4bd23249" +git-tree-sha1 = "8b3b6f87ce8f65a2b4f857528fd8d70086cd72b1" uuid = "c3611d14-8923-5661-9e6a-0046d554d3a4" -version = "0.10.0" +version = "0.11.0" weakdeps = ["SpecialFunctions"] [deps.ColorVectorSpace.extensions] @@ -174,9 +181,9 @@ weakdeps = ["SpecialFunctions"] [[deps.Colors]] deps = ["ColorTypes", "FixedPointNumbers", "Reexport"] -git-tree-sha1 = "362a287c3aa50601b0bc359053d5c2468f0e7ce0" +git-tree-sha1 = "64e15186f0aa277e174aa81798f7eb8598e0157e" uuid = "5ae59095-9a9b-59fe-a467-6f913c188581" -version = "0.12.11" +version = "0.13.0" [[deps.Compat]] deps = ["TOML", "UUIDs"] @@ -195,9 +202,9 @@ version = "1.1.1+0" [[deps.ConcurrentUtilities]] deps = ["Serialization", "Sockets"] -git-tree-sha1 = "ea32b83ca4fefa1768dc84e504cc0a94fb1ab8d1" +git-tree-sha1 = "d9d26935a0bcffc87d2613ce14c527c99fc543fd" uuid = "f0e56b4a-5159-44fe-b623-3e5288b988bb" -version = "2.4.2" +version = "2.5.0" [[deps.ConstructionBase]] git-tree-sha1 = "76219f1ed5771adbb096743bff43fb5fdd4c1157" @@ -222,9 +229,9 @@ version = "1.16.0" [[deps.DataStructures]] deps = ["Compat", "InteractiveUtils", "OrderedCollections"] -git-tree-sha1 = "1d0a14036acb104d9e89698bd408f63ab58cdc82" +git-tree-sha1 = "4e1fe97fdaed23e9dc21d4d664bea76b65fc50a0" uuid = "864edb3b-99cc-5e75-8d2d-829cb0a9cfe8" -version = "0.18.20" +version = "0.18.22" [[deps.DataValueInterfaces]] git-tree-sha1 = "bfc1187b79289637fa0ef6d4436ebdfe6905cbd6" @@ -236,10 +243,10 @@ deps = ["Printf"] uuid = "ade2ca70-3891-5945-98fb-dc099432e06a" [[deps.DelaunayTriangulation]] -deps = ["AdaptivePredicates", "EnumX", "ExactPredicates", "PrecompileTools", "Random"] -git-tree-sha1 = "89df54fbe66e5872d91d8c2cd3a375f660c3fd64" +deps = ["AdaptivePredicates", "EnumX", "ExactPredicates", "Random"] +git-tree-sha1 = "5620ff4ee0084a6ab7097a27ba0c19290200b037" uuid = "927a84f5-c5f4-47a5-9785-b46e178433df" -version = "1.6.1" +version = "1.6.4" [[deps.DelimitedFiles]] deps = ["Mmap"] @@ -270,9 +277,9 @@ uuid = "8ba89e20-285c-5b6f-9357-94700520ee1b" [[deps.Distributions]] deps = ["AliasTables", "FillArrays", "LinearAlgebra", "PDMats", "Printf", "QuadGK", "Random", "SpecialFunctions", "Statistics", "StatsAPI", "StatsBase", "StatsFuns"] -git-tree-sha1 = "3101c32aab536e7a27b1763c0797dba151b899ad" +git-tree-sha1 = "0b4190661e8a4e51a842070e7dd4fae440ddb7f4" uuid = "31c24e10-a181-5473-b8eb-7969acd0382f" -version = "0.25.113" +version = "0.25.118" [deps.Distributions.extensions] DistributionsChainRulesCoreExt = "ChainRulesCore" @@ -291,10 +298,9 @@ uuid = "968ba79b-81e4-546f-ab3a-2eecfa62a9db" version = "0.5.0" [[deps.DocStringExtensions]] -deps = ["LibGit2"] -git-tree-sha1 = "2fb1e02f2b635d0845df5d7c167fec4dd739b00d" +git-tree-sha1 = "e7b7e6f178525d17c720ab9c081e4ef04429f860" uuid = "ffbed154-4ef7-542d-bbb7-c09d3a79fcae" -version = "0.9.3" +version = "0.9.4" [[deps.Downloads]] deps = ["ArgTools", "FileWatching", "LibCURL", "NetworkOptions"] @@ -308,9 +314,9 @@ uuid = "5ae413db-bbd1-5e63-b57d-d24a61df00f5" version = "2.2.4+0" [[deps.EnumX]] -git-tree-sha1 = "bdb1942cd4c45e3c678fd11569d5cccd80976237" +git-tree-sha1 = "bddad79635af6aec424f53ed8aad5d7555dc6f00" uuid = "4e289a0a-7415-4d19-859d-a7e5c4648b56" -version = "1.0.4" +version = "1.0.5" [[deps.ExactPredicates]] deps = ["IntervalArithmetic", "Random", "StaticArrays"] @@ -320,20 +326,20 @@ version = "2.2.8" [[deps.ExceptionUnwrapping]] deps = ["Test"] -git-tree-sha1 = "dcb08a0d93ec0b1cdc4af184b26b591e9695423a" +git-tree-sha1 = "d36f682e590a83d63d1c7dbd287573764682d12a" uuid = "460bff9d-24e4-43bc-9d9f-a8973cb893f4" -version = "0.1.10" +version = "0.1.11" [[deps.Expat_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "1c6317308b9dc757616f0b5cb379db10494443a7" +git-tree-sha1 = "d55dffd9ae73ff72f1c0482454dcf2ec6c6c4a63" uuid = "2e619515-83b5-522b-bb60-26c02a35a201" -version = "2.6.2+0" +version = "2.6.5+0" [[deps.Extents]] -git-tree-sha1 = "81023caa0021a41712685887db1fc03db26f41f5" +git-tree-sha1 = "063512a13dbe9c40d999c439268539aa552d1ae6" uuid = "411431e0-e8b7-467b-b5e0-f676ba4f2910" -version = "0.1.4" +version = "0.1.5" [[deps.FFMPEG_jll]] deps = ["Artifacts", "Bzip2_jll", "FreeType2_jll", "FriBidi_jll", "JLLWrappers", "LAME_jll", "Libdl", "Ogg_jll", "OpenSSL_jll", "Opus_jll", "PCRE2_jll", "Zlib_jll", "libaom_jll", "libass_jll", "libfdk_aac_jll", "libvorbis_jll", "x264_jll", "x265_jll"] @@ -343,21 +349,25 @@ version = "6.1.2+0" [[deps.FFTW]] deps = ["AbstractFFTs", "FFTW_jll", "LinearAlgebra", "MKL_jll", "Preferences", "Reexport"] -git-tree-sha1 = "4820348781ae578893311153d69049a93d05f39d" +git-tree-sha1 = "7de7c78d681078f027389e067864a8d53bd7c3c9" uuid = "7a1cc6ca-52ef-59f5-83cd-3a7055c09341" -version = "1.8.0" +version = "1.8.1" [[deps.FFTW_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg"] git-tree-sha1 = "4d81ed14783ec49ce9f2e168208a12ce1815aa25" uuid = "f5851436-0d7a-5f13-b9de-f02708fd171a" -version = "3.3.10+1" +version = "3.3.10+3" [[deps.FileIO]] deps = ["Pkg", "Requires", "UUIDs"] -git-tree-sha1 = "91e0e5c68d02bcdaae76d3c8ceb4361e8f28d2e9" +git-tree-sha1 = "b66970a70db13f45b7e57fbda1736e1cf72174ea" uuid = "5789e2e9-d7fb-5bc7-8068-2c6fae9b9549" -version = "1.16.5" +version = "1.17.0" +weakdeps = ["HTTP"] + + [deps.FileIO.extensions] + HTTPExt = "HTTP" [[deps.FilePaths]] deps = ["FilePathsBase", "MacroTools", "Reexport", "Requires"] @@ -367,9 +377,9 @@ version = "0.8.3" [[deps.FilePathsBase]] deps = ["Compat", "Dates"] -git-tree-sha1 = "7878ff7172a8e6beedd1dea14bd27c3c6340d361" +git-tree-sha1 = "3bab2c5aa25e7840a4b065805c0cdfc01f3068d2" uuid = "48062228-2e41-5def-b9a4-89aafe57970f" -version = "0.9.22" +version = "0.9.24" weakdeps = ["Mmap", "Test"] [deps.FilePathsBase.extensions] @@ -399,9 +409,9 @@ version = "0.8.5" [[deps.Fontconfig_jll]] deps = ["Artifacts", "Bzip2_jll", "Expat_jll", "FreeType2_jll", "JLLWrappers", "Libdl", "Libuuid_jll", "Zlib_jll"] -git-tree-sha1 = "db16beca600632c95fc8aca29890d83788dd8b23" +git-tree-sha1 = "21fac3c77d7b5a9fc03b0ec503aa1a6392c34d2b" uuid = "a3f928ae-7b40-5064-980b-68af3947d34b" -version = "2.13.96+0" +version = "2.15.0+0" [[deps.Format]] git-tree-sha1 = "9c68794ef81b08086aeb32eeaf33531668d5f5fc" @@ -416,38 +426,38 @@ version = "4.1.1" [[deps.FreeType2_jll]] deps = ["Artifacts", "Bzip2_jll", "JLLWrappers", "Libdl", "Zlib_jll"] -git-tree-sha1 = "5c1d8ae0efc6c2e7b1fc502cbe25def8f661b7bc" +git-tree-sha1 = "2c5512e11c791d1baed2049c5652441b28fc6a31" uuid = "d7e528f0-a631-5988-bf34-fe36492bcfd7" -version = "2.13.2+0" +version = "2.13.4+0" [[deps.FreeTypeAbstraction]] deps = ["ColorVectorSpace", "Colors", "FreeType", "GeometryBasics"] -git-tree-sha1 = "77e2b094e61d939f9626181ab23d0b76e78f9fd3" +git-tree-sha1 = "d52e255138ac21be31fa633200b65e4e71d26802" uuid = "663a7486-cb36-511b-a19d-713bb74d65c9" -version = "0.10.5" +version = "0.10.6" [[deps.FriBidi_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "1ed150b39aebcc805c26b93a8d0122c940f64ce2" +git-tree-sha1 = "846f7026a9decf3679419122b49f8a1fdb48d2d5" uuid = "559328eb-81f9-559d-9380-de523a88c83c" -version = "1.0.14+0" +version = "1.0.16+0" [[deps.GeoFormatTypes]] -git-tree-sha1 = "59107c179a586f0fe667024c5eb7033e81333271" +git-tree-sha1 = "8e233d5167e63d708d41f87597433f59a0f213fe" uuid = "68eda718-8dee-11e9-39e7-89f7f65f511f" -version = "0.4.2" +version = "0.4.4" [[deps.GeoInterface]] -deps = ["Extents", "GeoFormatTypes"] -git-tree-sha1 = "826b4fd69438d9ce4d2b19de6bc2f970f45f0f88" +deps = ["DataAPI", "Extents", "GeoFormatTypes"] +git-tree-sha1 = "294e99f19869d0b0cb71aef92f19d03649d028d5" uuid = "cf35fbd7-0cd7-5166-be24-54bfbe79505f" -version = "1.3.8" +version = "1.4.1" [[deps.GeometryBasics]] -deps = ["EarCut_jll", "Extents", "GeoInterface", "IterTools", "LinearAlgebra", "StaticArrays", "StructArrays", "Tables"] -git-tree-sha1 = "b62f2b2d76cee0d61a2ef2b3118cd2a3215d3134" +deps = ["EarCut_jll", "Extents", "GeoInterface", "IterTools", "LinearAlgebra", "PrecompileTools", "Random", "StaticArrays"] +git-tree-sha1 = "65e3f5c519c3ec6a4c59f4c3ba21b6ff3add95b0" uuid = "5c1252a2-5f33-56bf-86c9-59e7332b4326" -version = "0.4.11" +version = "0.5.7" [[deps.Gettext_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "Libdl", "Libiconv_jll", "Pkg", "XML2_jll"] @@ -457,27 +467,27 @@ version = "0.21.0+0" [[deps.Giflib_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "0224cce99284d997f6880a42ef715a37c99338d1" +git-tree-sha1 = "6570366d757b50fabae9f4315ad74d2e40c0560a" uuid = "59f7168a-df46-5410-90c8-f2779963d0ec" -version = "5.2.2+0" +version = "5.2.3+0" [[deps.Glib_jll]] deps = ["Artifacts", "Gettext_jll", "JLLWrappers", "Libdl", "Libffi_jll", "Libiconv_jll", "Libmount_jll", "PCRE2_jll", "Zlib_jll"] -git-tree-sha1 = "674ff0db93fffcd11a3573986e550d66cd4fd71f" +git-tree-sha1 = "b0036b392358c80d2d2124746c2bf3d48d457938" uuid = "7746bdde-850d-59dc-9ae8-88ece973131d" -version = "2.80.5+0" +version = "2.82.4+0" [[deps.Graphite2_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg"] -git-tree-sha1 = "344bf40dcab1073aca04aa0df4fb092f920e4011" +git-tree-sha1 = "01979f9b37367603e2848ea225918a3b3861b606" uuid = "3b182d85-2403-5c21-9c21-1e1f0cc25472" -version = "1.3.14+0" +version = "1.3.14+1" [[deps.GridLayoutBase]] deps = ["GeometryBasics", "InteractiveUtils", "Observables"] -git-tree-sha1 = "fc713f007cff99ff9e50accba6373624ddd33588" +git-tree-sha1 = "dc6bed05c15523624909b3953686c5f5ffa10adc" uuid = "3955a311-db13-416c-9275-1d80ed98e5e9" -version = "0.11.0" +version = "0.11.1" [[deps.Grisu]] git-tree-sha1 = "53bb909d1151e57e2484c3d1b53e19552b887fb2" @@ -497,10 +507,10 @@ version = "0.17.2" MPI = "da04e1cc-30fd-572f-bb4f-1f8673147195" [[deps.HDF5_jll]] -deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "LLVMOpenMP_jll", "LazyArtifacts", "LibCURL_jll", "Libdl", "MPICH_jll", "MPIPreferences", "MPItrampoline_jll", "MicrosoftMPI_jll", "OpenMPI_jll", "OpenSSL_jll", "TOML", "Zlib_jll", "libaec_jll"] -git-tree-sha1 = "38c8874692d48d5440d5752d6c74b0c6b0b60739" +deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "LazyArtifacts", "LibCURL_jll", "Libdl", "MPICH_jll", "MPIPreferences", "MPItrampoline_jll", "MicrosoftMPI_jll", "OpenMPI_jll", "OpenSSL_jll", "TOML", "Zlib_jll", "libaec_jll"] +git-tree-sha1 = "e94f84da9af7ce9c6be049e9067e511e17ff89ec" uuid = "0234f1f7-429e-5d53-9886-15a909be8d59" -version = "1.14.2+1" +version = "1.14.6+0" [[deps.HTTP]] deps = ["Base64", "CodecZlib", "ConcurrentUtilities", "Dates", "ExceptionUnwrapping", "Logging", "LoggingExtras", "MbedTLS", "NetworkOptions", "OpenSSL", "PrecompileTools", "Random", "SimpleBufferStream", "Sockets", "URIs", "UUIDs"] @@ -510,21 +520,21 @@ version = "1.10.15" [[deps.HarfBuzz_jll]] deps = ["Artifacts", "Cairo_jll", "Fontconfig_jll", "FreeType2_jll", "Glib_jll", "Graphite2_jll", "JLLWrappers", "Libdl", "Libffi_jll"] -git-tree-sha1 = "401e4f3f30f43af2c8478fc008da50096ea5240f" +git-tree-sha1 = "55c53be97790242c29031e5cd45e8ac296dadda3" uuid = "2e76f6c2-a576-52d4-95c1-20adfe4de566" -version = "8.3.1+0" +version = "8.5.0+0" [[deps.Hwloc_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "50aedf345a709ab75872f80a2779568dc0bb461b" +git-tree-sha1 = "f93a9ce66cd89c9ba7a4695a47fd93b4c6bc59fa" uuid = "e33a78d0-f292-5ffc-b300-72abe9b543c8" -version = "2.11.2+1" +version = "2.12.0+0" [[deps.HypergeometricFunctions]] deps = ["LinearAlgebra", "OpenLibm_jll", "SpecialFunctions"] -git-tree-sha1 = "b1c2585431c382e3fe5805874bda6aea90a95de9" +git-tree-sha1 = "68c173f4f449de5b438ee67ed0c9c748dc31a2ec" uuid = "34004b35-14d8-5ef3-9330-4cdb6864b03a" -version = "0.3.25" +version = "0.3.28" [[deps.Hyperscript]] deps = ["Test"] @@ -580,9 +590,9 @@ version = "0.1.5" [[deps.IntelOpenMP_jll]] deps = ["Artifacts", "JLLWrappers", "LazyArtifacts", "Libdl"] -git-tree-sha1 = "10bd689145d2c3b2a9844005d01087cc1194e79e" +git-tree-sha1 = "0f14a5456bdc6b9731a5682f439a672750a09e48" uuid = "1d5cc7b8-4909-519e-a0f8-d0f5ad9712d0" -version = "2024.2.1+0" +version = "2025.0.4+0" [[deps.InteractiveUtils]] deps = ["Markdown"] @@ -599,10 +609,10 @@ weakdeps = ["Unitful"] InterpolationsUnitfulExt = "Unitful" [[deps.IntervalArithmetic]] -deps = ["CRlibm_jll", "LinearAlgebra", "MacroTools", "RoundingEmulator"] -git-tree-sha1 = "24c095b1ec7ee58b936985d31d5df92f9b9cfebb" +deps = ["CRlibm_jll", "LinearAlgebra", "MacroTools", "OpenBLASConsistentFPCSR_jll", "RoundingEmulator"] +git-tree-sha1 = "dfbf101df925acf1caa3b15a00b574887cd8472d" uuid = "d1acc4aa-44c8-5952-acd4-ba5d80a2a253" -version = "0.22.19" +version = "0.22.26" [deps.IntervalArithmetic.extensions] IntervalArithmeticDiffRulesExt = "DiffRules" @@ -638,9 +648,9 @@ weakdeps = ["Dates", "Test"] InverseFunctionsTestExt = "Test" [[deps.IrrationalConstants]] -git-tree-sha1 = "630b497eafcc20001bba38a4651b327dcfc491d2" +git-tree-sha1 = "e2222959fbc6c19554dc15174c81bf7bf3aa691c" uuid = "92d709cd-6900-40b7-9082-c6be49f344b6" -version = "0.2.2" +version = "0.2.4" [[deps.Isoband]] deps = ["isoband_jll"] @@ -660,9 +670,9 @@ version = "1.0.0" [[deps.JLLWrappers]] deps = ["Artifacts", "Preferences"] -git-tree-sha1 = "be3dc50a92e5a386872a493a10050136d4703f9b" +git-tree-sha1 = "a007feb38b422fbdab534406aeca1b86823cb4d6" uuid = "692b3bcd-3c85-4b1f-b108-f13ce0eb3210" -version = "1.6.1" +version = "1.7.0" [[deps.JSON]] deps = ["Dates", "Mmap", "Parsers", "Unicode"] @@ -672,9 +682,9 @@ version = "0.21.4" [[deps.JSON3]] deps = ["Dates", "Mmap", "Parsers", "PrecompileTools", "StructTypes", "UUIDs"] -git-tree-sha1 = "1d322381ef7b087548321d3f878cb4c9bd8f8f9b" +git-tree-sha1 = "196b41e5a854b387d99e5ede2de3fcb4d0422aae" uuid = "0f8b85d8-7281-11e9-16c2-39a750bddbf1" -version = "1.14.1" +version = "1.14.2" [deps.JSON3.extensions] JSON3ArrowExt = ["ArrowTypes"] @@ -684,15 +694,15 @@ version = "1.14.1" [[deps.JpegTurbo]] deps = ["CEnum", "FileIO", "ImageCore", "JpegTurbo_jll", "TOML"] -git-tree-sha1 = "fa6d0bcff8583bac20f1ffa708c3913ca605c611" +git-tree-sha1 = "9496de8fb52c224a2e3f9ff403947674517317d9" uuid = "b835a17e-a41a-41e7-81f0-2f016b05efe0" -version = "0.1.5" +version = "0.1.6" [[deps.JpegTurbo_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "25ee0be4d43d0269027024d75a24c24d6c6e590c" +git-tree-sha1 = "eac1206917768cb54957c65a615460d87b455fc1" uuid = "aacddb02-875f-59d6-b918-886e6ef4fbf8" -version = "3.0.4+0" +version = "3.1.1+0" [[deps.KernelDensity]] deps = ["Distributions", "DocStringExtensions", "FFTW", "Interpolations", "StatsBase"] @@ -708,9 +718,9 @@ version = "3.100.2+0" [[deps.LERC_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "36bdbc52f13a7d1dcb0f3cd694e01677a515655b" +git-tree-sha1 = "aaafe88dccbd957a8d82f7d05be9b69172e0cee3" uuid = "88015f11-f218-50d7-93a8-a6af411a945d" -version = "4.0.0+0" +version = "4.0.1+0" [[deps.LLVMOpenMP_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] @@ -720,9 +730,9 @@ version = "18.1.7+0" [[deps.LZO_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "854a9c268c43b77b0a27f22d7fab8d33cdb3a731" +git-tree-sha1 = "1c602b1127f4751facb671441ca72715cc95938a" uuid = "dd4b983a-f0e5-5f8d-a1b7-129d4a5fb1ac" -version = "2.10.2+1" +version = "2.10.3+0" [[deps.LaTeXStrings]] git-tree-sha1 = "dda21b8cbd6a6c40d9d02a73230f9d70fed6918c" @@ -767,9 +777,9 @@ uuid = "8f399da3-3557-5675-b5ff-fb832c97cbdb" [[deps.Libffi_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg"] -git-tree-sha1 = "0b4a5d71f3e5200a7dff793393e09dfc2d874290" +git-tree-sha1 = "27ecae93dd25ee0909666e6835051dd684cc035e" uuid = "e9f186c6-92d2-5b65-8a66-fee21dc1b490" -version = "3.2.2+1" +version = "3.2.2+2" [[deps.Libgcrypt_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Libgpg_error_jll"] @@ -778,40 +788,40 @@ uuid = "d4300ac3-e22c-5743-9152-c294e39db1e4" version = "1.11.0+0" [[deps.Libglvnd_jll]] -deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg", "Xorg_libX11_jll", "Xorg_libXext_jll"] -git-tree-sha1 = "6f73d1dd803986947b2c750138528a999a6c7733" +deps = ["Artifacts", "JLLWrappers", "Libdl", "Xorg_libX11_jll", "Xorg_libXext_jll"] +git-tree-sha1 = "ff3b4b9d35de638936a525ecd36e86a8bb919d11" uuid = "7e76a0d4-f3c7-5321-8279-8d96eeed0f29" -version = "1.6.0+0" +version = "1.7.0+0" [[deps.Libgpg_error_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "c6ce1e19f3aec9b59186bdf06cdf3c4fc5f5f3e6" +git-tree-sha1 = "df37206100d39f79b3376afb6b9cee4970041c61" uuid = "7add5ba3-2f88-524e-9cd5-f83b8a55f7b8" -version = "1.50.0+0" +version = "1.51.1+0" [[deps.Libiconv_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "61dfdba58e585066d8bce214c5a51eaa0539f269" +git-tree-sha1 = "be484f5c92fad0bd8acfef35fe017900b0b73809" uuid = "94ce4f54-9a6c-5748-9c1c-f9c7231a4531" -version = "1.17.0+1" +version = "1.18.0+0" [[deps.Libmount_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "0c4f9c4f1a50d8f35048fa0532dabbadf702f81e" +git-tree-sha1 = "89211ea35d9df5831fca5d33552c02bd33878419" uuid = "4b2f31a3-9ecc-558c-b454-b3730dcb73e9" -version = "2.40.1+0" +version = "2.40.3+0" [[deps.Libtiff_jll]] deps = ["Artifacts", "JLLWrappers", "JpegTurbo_jll", "LERC_jll", "Libdl", "XZ_jll", "Zlib_jll", "Zstd_jll"] -git-tree-sha1 = "b404131d06f7886402758c9ce2214b636eb4d54a" +git-tree-sha1 = "4ab7581296671007fc33f07a721631b8855f4b1d" uuid = "89763e89-9b03-5906-acba-b20f662cd828" -version = "4.7.0+0" +version = "4.7.1+0" [[deps.Libuuid_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "5ee6203157c120d79034c748a2acba45b82b8807" +git-tree-sha1 = "e888ad02ce716b319e6bdb985d2ef300e7089889" uuid = "38a345b3-de98-5d2b-a5d3-14cd9215e700" -version = "2.40.1+0" +version = "2.40.3+0" [[deps.LinearAlgebra]] deps = ["Libdl", "OpenBLAS_jll", "libblastrampoline_jll"] @@ -819,9 +829,9 @@ uuid = "37e2e46d-f89d-539d-b4ee-838fcccc9c8e" [[deps.LogExpFunctions]] deps = ["DocStringExtensions", "IrrationalConstants", "LinearAlgebra"] -git-tree-sha1 = "a2d09619db4e765091ee5c6ffe8872849de0feea" +git-tree-sha1 = "13ca9e2586b89836fd20cccf56e57e2b9ae7f38f" uuid = "2ab3a3ac-af41-5b50-aa03-7779005ae688" -version = "0.3.28" +version = "0.3.29" [deps.LogExpFunctions.extensions] LogExpFunctionsChainRulesCoreExt = "ChainRulesCore" @@ -849,21 +859,21 @@ uuid = "23992714-dd62-5051-b70f-ba57cb901cac" version = "0.10.7" [[deps.MIMEs]] -git-tree-sha1 = "1833212fd6f580c20d4291da9c1b4e8a655b128e" +git-tree-sha1 = "c64d943587f7187e751162b3b84445bbbd79f691" uuid = "6c6e2e6c-3030-632d-7369-2d6c69616d65" -version = "1.0.0" +version = "1.1.0" [[deps.MKL_jll]] deps = ["Artifacts", "IntelOpenMP_jll", "JLLWrappers", "LazyArtifacts", "Libdl", "oneTBB_jll"] -git-tree-sha1 = "f046ccd0c6db2832a9f639e2c669c6fe867e5f4f" +git-tree-sha1 = "5de60bc6cb3899cd318d80d627560fae2e2d99ae" uuid = "856f044c-d86e-5d09-b602-aeab76dc8ba7" -version = "2024.2.0+0" +version = "2025.0.1+1" [[deps.MPICH_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "Hwloc_jll", "JLLWrappers", "LazyArtifacts", "Libdl", "MPIPreferences", "TOML"] -git-tree-sha1 = "7715e65c47ba3941c502bffb7f266a41a7f54423" +git-tree-sha1 = "3aa3210044138a1749dbd350a9ba8680869eb503" uuid = "7cb0a576-ebde-5e09-9194-50597f1243b4" -version = "4.2.3+0" +version = "4.3.0+1" [[deps.MPIPreferences]] deps = ["Libdl", "Preferences"] @@ -873,27 +883,26 @@ version = "0.1.11" [[deps.MPItrampoline_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "LazyArtifacts", "Libdl", "MPIPreferences", "TOML"] -git-tree-sha1 = "70e830dab5d0775183c99fc75e4c24c614ed7142" +git-tree-sha1 = "ff91ca13c7c472cef700f301c8d752bc2aaff1a8" uuid = "f1f71cc9-e9ae-5b93-9b94-4fe0e1ad3748" -version = "5.5.1+0" +version = "5.5.3+0" [[deps.MacroTools]] -deps = ["Markdown", "Random"] -git-tree-sha1 = "2fa9ee3e63fd3a4f7a9a4f4744a52f4856de82df" +git-tree-sha1 = "72aebe0b5051e5143a079a4685a46da330a40472" uuid = "1914dd2f-81c6-5fcd-8719-6d5c9610ff09" -version = "0.5.13" +version = "0.5.15" [[deps.Makie]] -deps = ["Animations", "Base64", "CRC32c", "ColorBrewer", "ColorSchemes", "ColorTypes", "Colors", "Contour", "Dates", "DelaunayTriangulation", "Distributions", "DocStringExtensions", "Downloads", "FFMPEG_jll", "FileIO", "FilePaths", "FixedPointNumbers", "Format", "FreeType", "FreeTypeAbstraction", "GeometryBasics", "GridLayoutBase", "ImageBase", "ImageIO", "InteractiveUtils", "Interpolations", "IntervalSets", "InverseFunctions", "Isoband", "KernelDensity", "LaTeXStrings", "LinearAlgebra", "MacroTools", "MakieCore", "Markdown", "MathTeXEngine", "Observables", "OffsetArrays", "Packing", "PlotUtils", "PolygonOps", "PrecompileTools", "Printf", "REPL", "Random", "RelocatableFolders", "Scratch", "ShaderAbstractions", "Showoff", "SignedDistanceFields", "SparseArrays", "Statistics", "StatsBase", "StatsFuns", "StructArrays", "TriplotBase", "UnicodeFun", "Unitful"] -git-tree-sha1 = "5e4e0e027642293da251bf35dac408d692ccba8b" +deps = ["Animations", "Base64", "CRC32c", "ColorBrewer", "ColorSchemes", "ColorTypes", "Colors", "Contour", "Dates", "DelaunayTriangulation", "Distributions", "DocStringExtensions", "Downloads", "FFMPEG_jll", "FileIO", "FilePaths", "FixedPointNumbers", "Format", "FreeType", "FreeTypeAbstraction", "GeometryBasics", "GridLayoutBase", "ImageBase", "ImageIO", "InteractiveUtils", "Interpolations", "IntervalSets", "InverseFunctions", "Isoband", "KernelDensity", "LaTeXStrings", "LinearAlgebra", "MacroTools", "MakieCore", "Markdown", "MathTeXEngine", "Observables", "OffsetArrays", "PNGFiles", "Packing", "PlotUtils", "PolygonOps", "PrecompileTools", "Printf", "REPL", "Random", "RelocatableFolders", "Scratch", "ShaderAbstractions", "Showoff", "SignedDistanceFields", "SparseArrays", "Statistics", "StatsBase", "StatsFuns", "StructArrays", "TriplotBase", "UnicodeFun", "Unitful"] +git-tree-sha1 = "e64b545d25e05a609521bfc36724baa072bfd31a" uuid = "ee78f7c6-11fb-53f2-987a-cfe4a2b5a57a" -version = "0.21.16" +version = "0.22.2" [[deps.MakieCore]] deps = ["ColorTypes", "GeometryBasics", "IntervalSets", "Observables"] -git-tree-sha1 = "ae4dbe0fcf1594ed98594e5f4ee685295a2a6f74" +git-tree-sha1 = "605d6e8f2b7eba7f5bc6a16d297475075d5ea775" uuid = "20f20a25-4f0e-4fdf-b5d1-57303727442b" -version = "0.8.10" +version = "0.9.1" [[deps.MappedArrays]] git-tree-sha1 = "2dab0221fe2b0f2cb6754eaa743cc266339f527e" @@ -929,9 +938,9 @@ version = "0.29.0" [[deps.MicrosoftMPI_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg"] -git-tree-sha1 = "f12a29c4400ba812841c6ace3f4efbb6dbb3ba01" +git-tree-sha1 = "bc95bf4149bf535c09602e3acdf950d9b4376227" uuid = "9237b28f-5490-5468-be7b-bb81f5f5e6cf" -version = "10.1.4+2" +version = "10.1.4+3" [[deps.Missings]] deps = ["DataAPI"] @@ -976,11 +985,11 @@ version = "1.2.0" [[deps.NyxWidgets]] deps = ["Bonito", "Colors", "Format", "LazyArtifacts", "Observables"] -git-tree-sha1 = "e18ab14817871c54419e4cef12f9fc4dc589f6fe" +git-tree-sha1 = "d5addf940e4265b3ca2a6fe29b8ff24bf3b13b98" repo-rev = "main" repo-url = "https://gitlab.com/dbc-nyx/NyxWidgets.jl" uuid = "c288fd06-43d3-4b04-8307-797133353e2e" -version = "0.2.0" +version = "0.2.1" [[deps.Observables]] git-tree-sha1 = "7438a59546cf62428fc9d1bc94729146d37a7225" @@ -996,9 +1005,9 @@ uuid = "6317928a-6b1a-42e8-b853-b8e2fc3e9ca3" version = "0.2.4" [[deps.OffsetArrays]] -git-tree-sha1 = "1a27764e945a152f7ca7efa04de513d473e9542e" +git-tree-sha1 = "a414039192a155fb38c4599a60110f0018c6ec82" uuid = "6fe1bfb0-de20-5000-8ca7-80f57d26f881" -version = "1.14.1" +version = "1.16.0" weakdeps = ["Adapt"] [deps.OffsetArrays.extensions] @@ -1010,6 +1019,12 @@ git-tree-sha1 = "887579a3eb005446d514ab7aeac5d1d027658b8f" uuid = "e7412a2a-1a6e-54c0-be00-318e2571c051" version = "1.3.5+1" +[[deps.OpenBLASConsistentFPCSR_jll]] +deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "Libdl"] +git-tree-sha1 = "567515ca155d0020a45b05175449b499c63e7015" +uuid = "6cdc7f73-28fd-5e50-80fb-958a8875b1af" +version = "0.3.29+0" + [[deps.OpenBLAS_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "Libdl"] uuid = "4536629a-c528-5b80-bd46-f80d51c5b363" @@ -1034,9 +1049,9 @@ version = "0.8.1+4" [[deps.OpenMPI_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "Hwloc_jll", "JLLWrappers", "LazyArtifacts", "Libdl", "MPIPreferences", "TOML", "Zlib_jll"] -git-tree-sha1 = "bfce6d523861a6c562721b262c0d1aaeead2647f" +git-tree-sha1 = "da913f03f17b449951e0461da960229d4a3d1a8c" uuid = "fe0851c0-eecd-5654-98d4-656369965a5c" -version = "5.0.5+0" +version = "5.0.7+1" [[deps.OpenSSL]] deps = ["BitFlags", "Dates", "MozillaCACerts_jll", "OpenSSL_jll", "Sockets"] @@ -1046,15 +1061,15 @@ version = "1.4.3" [[deps.OpenSSL_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "7493f61f55a6cce7325f197443aa80d32554ba10" +git-tree-sha1 = "a9697f1d06cc3eb3fb3ad49cc67f2cfabaac31ea" uuid = "458c3c95-2e84-50aa-8efc-19380b2a3a95" -version = "3.0.15+1" +version = "3.0.16+0" [[deps.OpenSpecFun_jll]] -deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "Libdl", "Pkg"] -git-tree-sha1 = "13652491f6856acfd2db29360e1bbcd4565d04f1" +deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "Libdl"] +git-tree-sha1 = "1346c9208249809840c91b26703912dff463d335" uuid = "efe28fd5-8261-553b-a9e1-b2916fc3738e" -version = "0.5.5+0" +version = "0.5.6+0" [[deps.Opus_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] @@ -1063,9 +1078,9 @@ uuid = "91d4177d-7536-5919-b921-800302f37372" version = "1.3.3+0" [[deps.OrderedCollections]] -git-tree-sha1 = "dfdf5519f235516220579f949664f1bf44e741c5" +git-tree-sha1 = "cc4054e898b852042d7b503313f7ad03de99c3dd" uuid = "bac558e1-5e72-5ebc-8fee-abe8a469f55d" -version = "1.6.3" +version = "1.8.0" [[deps.Oxygen]] deps = ["DataStructures", "Dates", "HTTP", "JSON3", "MIMEs", "Reexport", "RelocatableFolders", "Requires", "Sockets", "Statistics", "StructTypes"] @@ -1080,21 +1095,21 @@ version = "10.42.0+1" [[deps.PDMats]] deps = ["LinearAlgebra", "SparseArrays", "SuiteSparse"] -git-tree-sha1 = "949347156c25054de2db3b166c52ac4728cbad65" +git-tree-sha1 = "48566789a6d5f6492688279e22445002d171cf76" uuid = "90014a1f-27ba-587c-ab20-58faa44d9150" -version = "0.11.31" +version = "0.11.33" [[deps.PNGFiles]] deps = ["Base64", "CEnum", "ImageCore", "IndirectArrays", "OffsetArrays", "libpng_jll"] -git-tree-sha1 = "67186a2bc9a90f9f85ff3cc8277868961fb57cbd" +git-tree-sha1 = "cf181f0b1e6a18dfeb0ee8acc4a9d1672499626c" uuid = "f57f5aa1-a3ce-4bc8-8ab9-96f992907883" -version = "0.4.3" +version = "0.4.4" [[deps.Packing]] deps = ["GeometryBasics"] -git-tree-sha1 = "ec3edfe723df33528e085e632414499f26650501" +git-tree-sha1 = "bc5bf2ea3d5351edf285a06b0016788a121ce92c" uuid = "19eb6ba3-879d-56ad-ad62-d5c202156566" -version = "0.5.0" +version = "0.5.1" [[deps.PaddedViews]] deps = ["OffsetArrays"] @@ -1110,9 +1125,9 @@ version = "2.8.1" [[deps.Pixman_jll]] deps = ["Artifacts", "CompilerSupportLibraries_jll", "JLLWrappers", "LLVMOpenMP_jll", "Libdl"] -git-tree-sha1 = "35621f10a7531bc8fa58f74610b1bfb70a3cfc6b" +git-tree-sha1 = "db76b1ecd5e9715f3d043cec13b2ec93ce015d53" uuid = "30392449-352a-5448-841d-b1acce4e97dc" -version = "0.43.4+0" +version = "0.44.2+0" [[deps.Pkg]] deps = ["Artifacts", "Dates", "Downloads", "FileWatching", "LibGit2", "Libdl", "Logging", "Markdown", "Printf", "REPL", "Random", "SHA", "Serialization", "TOML", "Tar", "UUIDs", "p7zip_jll"] @@ -1167,9 +1182,9 @@ uuid = "92933f4c-e287-5a05-a399-4b506db050ca" version = "1.10.2" [[deps.PtrArrays]] -git-tree-sha1 = "77a42d78b6a92df47ab37e177b2deac405e1c88f" +git-tree-sha1 = "1d36ef11a9aaf1e8b74dacc6a731dd1de8fd493d" uuid = "43287f4e-b6f4-7ad1-bb20-aadabca52c3d" -version = "1.2.1" +version = "1.3.0" [[deps.QOI]] deps = ["ColorTypes", "FileIO", "FixedPointNumbers"] @@ -1179,9 +1194,9 @@ version = "1.0.1" [[deps.QuadGK]] deps = ["DataStructures", "LinearAlgebra"] -git-tree-sha1 = "cda3b045cf9ef07a08ad46731f5a3165e56cf3da" +git-tree-sha1 = "9da16da70037ba9d701192e27befedefb91ec284" uuid = "1fd47b50-473d-5c70-9696-f719f8f3bcdc" -version = "2.11.1" +version = "2.11.2" [deps.QuadGK.extensions] QuadGKEnzymeExt = "Enzyme" @@ -1243,9 +1258,9 @@ version = "1.0.1" [[deps.Requires]] deps = ["UUIDs"] -git-tree-sha1 = "838a3a4188e2ded87a4f9f184b4b0d78a1e91cb7" +git-tree-sha1 = "62389eeff14780bfe55195b7204c0d8738436d64" uuid = "ae029012-a4dd-5104-9daa-d747884805df" -version = "1.3.0" +version = "1.3.1" [[deps.Rmath]] deps = ["Random", "Rmath_jll"] @@ -1280,9 +1295,9 @@ version = "0.7.0" [[deps.SIMD]] deps = ["PrecompileTools"] -git-tree-sha1 = "52af86e35dd1b177d051b12681e1c581f53c281b" +git-tree-sha1 = "fea870727142270bdf7624ad675901a1ee3b4c87" uuid = "fdea26ae-647d-5447-a871-4b548cad5224" -version = "3.7.0" +version = "3.7.1" [[deps.Scratch]] deps = ["Dates"] @@ -1294,10 +1309,10 @@ version = "1.2.1" uuid = "9e88b42a-f829-5b0c-bbe9-9e923198166b" [[deps.ShaderAbstractions]] -deps = ["ColorTypes", "FixedPointNumbers", "GeometryBasics", "LinearAlgebra", "Observables", "StaticArrays", "StructArrays", "Tables"] -git-tree-sha1 = "79123bc60c5507f035e6d1d9e563bb2971954ec8" +deps = ["ColorTypes", "FixedPointNumbers", "GeometryBasics", "LinearAlgebra", "Observables", "StaticArrays"] +git-tree-sha1 = "818554664a2e01fc3784becb2eb3a82326a604b6" uuid = "65257c39-d410-5151-9873-9b3e5be5013e" -version = "0.4.1" +version = "0.5.0" [[deps.SharedArrays]] deps = ["Distributed", "Mmap", "Random", "Serialization"] @@ -1348,9 +1363,9 @@ version = "1.10.0" [[deps.SpecialFunctions]] deps = ["IrrationalConstants", "LogExpFunctions", "OpenLibm_jll", "OpenSpecFun_jll"] -git-tree-sha1 = "2f5d4697f21388cbe1ff299430dd169ef97d7e14" +git-tree-sha1 = "64cca0c26b4f31ba18f13f6c12af7c85f478cfde" uuid = "276daf66-3868-5448-9aa4-cd146d93841b" -version = "2.4.0" +version = "2.5.0" weakdeps = ["ChainRulesCore"] [deps.SpecialFunctions.extensions] @@ -1370,9 +1385,9 @@ version = "0.1.1" [[deps.StaticArrays]] deps = ["LinearAlgebra", "PrecompileTools", "Random", "StaticArraysCore"] -git-tree-sha1 = "777657803913ffc7e8cc20f0fd04b634f871af8f" +git-tree-sha1 = "0feb6b9031bd5c51f9072393eb5ab3efd31bf9e4" uuid = "90137ffa-7385-5640-81b9-e52037218182" -version = "1.9.8" +version = "1.9.13" weakdeps = ["ChainRulesCore", "Statistics"] [deps.StaticArrays.extensions] @@ -1396,10 +1411,10 @@ uuid = "82ae8749-77ed-4fe6-ae5f-f523153014b0" version = "1.7.0" [[deps.StatsBase]] -deps = ["DataAPI", "DataStructures", "LinearAlgebra", "LogExpFunctions", "Missings", "Printf", "Random", "SortingAlgorithms", "SparseArrays", "Statistics", "StatsAPI"] -git-tree-sha1 = "5cf7606d6cef84b543b483848d4ae08ad9832b21" +deps = ["AliasTables", "DataAPI", "DataStructures", "LinearAlgebra", "LogExpFunctions", "Missings", "Printf", "Random", "SortingAlgorithms", "SparseArrays", "Statistics", "StatsAPI"] +git-tree-sha1 = "29321314c920c26684834965ec2ce0dacc9cf8e5" uuid = "2913bbd2-ae8a-5f71-8c99-4fb6c76f3a91" -version = "0.34.3" +version = "0.34.4" [[deps.StatsFuns]] deps = ["HypergeometricFunctions", "IrrationalConstants", "LogExpFunctions", "Reexport", "Rmath", "SpecialFunctions"] @@ -1414,19 +1429,22 @@ weakdeps = ["ChainRulesCore", "InverseFunctions"] [[deps.StructArrays]] deps = ["ConstructionBase", "DataAPI", "Tables"] -git-tree-sha1 = "f4dc295e983502292c4c3f951dbb4e985e35b3be" +git-tree-sha1 = "5a3a31c41e15a1e042d60f2f4942adccba05d3c9" uuid = "09ab397b-f2b6-538f-b94a-2f83cf4a842a" -version = "0.6.18" +version = "0.7.0" [deps.StructArrays.extensions] StructArraysAdaptExt = "Adapt" - StructArraysGPUArraysCoreExt = "GPUArraysCore" + StructArraysGPUArraysCoreExt = ["GPUArraysCore", "KernelAbstractions"] + StructArraysLinearAlgebraExt = "LinearAlgebra" StructArraysSparseArraysExt = "SparseArrays" StructArraysStaticArraysExt = "StaticArrays" [deps.StructArrays.weakdeps] Adapt = "79e6a3ab-5dfb-504d-930d-738a2a938a0e" GPUArraysCore = "46192b85-c4d5-4398-a991-12ede77f4527" + KernelAbstractions = "63c18a36-062a-441e-b654-da1e3ab1ce7c" + LinearAlgebra = "37e2e46d-f89d-539d-b4ee-838fcccc9c8e" SparseArrays = "2f01184e-e22b-5df5-ae63-d93ebab69eaf" StaticArrays = "90137ffa-7385-5640-81b9-e52037218182" @@ -1493,9 +1511,9 @@ version = "0.1.1" [[deps.TiffImages]] deps = ["ColorTypes", "DataStructures", "DocStringExtensions", "FileIO", "FixedPointNumbers", "IndirectArrays", "Inflate", "Mmap", "OffsetArrays", "PkgVersion", "ProgressMeter", "SIMD", "UUIDs"] -git-tree-sha1 = "0248b1b2210285652fbc67fd6ced9bf0394bcfec" +git-tree-sha1 = "f21231b166166bebc73b99cea236071eb047525b" uuid = "731e570b-9d59-4bfa-96dc-6df516fadf69" -version = "0.11.1" +version = "0.11.3" [[deps.TranscodingStreams]] git-tree-sha1 = "0c45878dcfdcfa8480052b6ab162cdd138781742" @@ -1514,9 +1532,9 @@ uuid = "981d1d27-644d-49a2-9326-4793e63143c3" version = "0.1.0" [[deps.URIs]] -git-tree-sha1 = "67db6cc7b3821e19ebe75791a9dd19c9b1188f2b" +git-tree-sha1 = "cbbebadbcc76c5ca1cc4b4f3b0614b3e603b5000" uuid = "5c2747f8-b7ea-4ff2-ba2e-563bfd36b1d4" -version = "1.5.1" +version = "1.5.2" [[deps.UUIDs]] deps = ["Random", "SHA"] @@ -1533,9 +1551,9 @@ version = "0.4.1" [[deps.Unitful]] deps = ["Dates", "LinearAlgebra", "Random"] -git-tree-sha1 = "d95fe458f26209c66a187b1114df96fd70839efd" +git-tree-sha1 = "c0667a8e676c53d390a09dc6870b3d8d6650e2bf" uuid = "1986cc42-f94f-5a68-af5c-568840ba703d" -version = "1.21.0" +version = "1.22.0" weakdeps = ["ConstructionBase", "InverseFunctions"] [deps.Unitful.extensions] @@ -1544,9 +1562,9 @@ weakdeps = ["ConstructionBase", "InverseFunctions"] [[deps.WGLMakie]] deps = ["Bonito", "Colors", "FileIO", "FreeTypeAbstraction", "GeometryBasics", "Hyperscript", "LinearAlgebra", "Makie", "Observables", "PNGFiles", "PrecompileTools", "RelocatableFolders", "ShaderAbstractions", "StaticArrays"] -git-tree-sha1 = "8ac9150de978e8215e7c9ab437d6f0a673748999" +git-tree-sha1 = "94de96cef3e4b9ec09096f6e5e9814041d59300c" uuid = "276b4fcb-3e11-5398-bf8b-a0c2d153d008" -version = "0.10.16" +version = "0.11.2" [[deps.WebP]] deps = ["CEnum", "ColorTypes", "FileIO", "FixedPointNumbers", "ImageCore", "libwebp_jll"] @@ -1568,69 +1586,69 @@ version = "1.0.0" [[deps.XML2_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Libiconv_jll", "Zlib_jll"] -git-tree-sha1 = "6a451c6f33a176150f315726eba8b92fbfdb9ae7" +git-tree-sha1 = "b8b243e47228b4a3877f1dd6aee0c5d56db7fcf4" uuid = "02c8fc9c-b97f-50b9-bbe4-9be30ff0a78a" -version = "2.13.4+0" +version = "2.13.6+1" [[deps.XSLT_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Libgcrypt_jll", "Libgpg_error_jll", "Libiconv_jll", "XML2_jll", "Zlib_jll"] -git-tree-sha1 = "a54ee957f4c86b526460a720dbc882fa5edcbefc" +git-tree-sha1 = "7d1671acbe47ac88e981868a078bd6b4e27c5191" uuid = "aed1982a-8fda-507f-9586-7b0439959a61" -version = "1.1.41+0" +version = "1.1.42+0" [[deps.XZ_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "15e637a697345f6743674f1322beefbc5dcd5cfc" +git-tree-sha1 = "56c6604ec8b2d82cc4cfe01aa03b00426aac7e1f" uuid = "ffd25f8a-64ca-5728-b0f7-c24cf3aae800" -version = "5.6.3+0" +version = "5.6.4+1" [[deps.Xorg_libX11_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Xorg_libxcb_jll", "Xorg_xtrans_jll"] -git-tree-sha1 = "afead5aba5aa507ad5a3bf01f58f82c8d1403495" +git-tree-sha1 = "9dafcee1d24c4f024e7edc92603cedba72118283" uuid = "4f6342f7-b3d2-589e-9d20-edeb45f2b2bc" -version = "1.8.6+0" +version = "1.8.6+3" [[deps.Xorg_libXau_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "6035850dcc70518ca32f012e46015b9beeda49d8" +git-tree-sha1 = "e9216fdcd8514b7072b43653874fd688e4c6c003" uuid = "0c0b7dd1-d40b-584c-a123-a41640f87eec" -version = "1.0.11+0" +version = "1.0.12+0" [[deps.Xorg_libXdmcp_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "34d526d318358a859d7de23da945578e8e8727b7" +git-tree-sha1 = "89799ae67c17caa5b3b5a19b8469eeee474377db" uuid = "a3789734-cfe1-5b06-b2d0-1dd0d9d62d05" -version = "1.1.4+0" +version = "1.1.5+0" [[deps.Xorg_libXext_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Xorg_libX11_jll"] -git-tree-sha1 = "d2d1a5c49fae4ba39983f63de6afcbea47194e85" +git-tree-sha1 = "d7155fea91a4123ef59f42c4afb5ab3b4ca95058" uuid = "1082639a-0dae-5f34-9b06-72781eeb8cb3" -version = "1.3.6+0" +version = "1.3.6+3" [[deps.Xorg_libXrender_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Xorg_libX11_jll"] -git-tree-sha1 = "47e45cd78224c53109495b3e324df0c37bb61fbe" +git-tree-sha1 = "a490c6212a0e90d2d55111ac956f7c4fa9c277a6" uuid = "ea2f1a96-1ddc-540d-b46f-429655e07cfa" -version = "0.9.11+0" +version = "0.9.11+1" [[deps.Xorg_libpthread_stubs_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "8fdda4c692503d44d04a0603d9ac0982054635f9" +git-tree-sha1 = "c57201109a9e4c0585b208bb408bc41d205ac4e9" uuid = "14d82f49-176c-5ed1-bb49-ad3f5cbd8c74" -version = "0.1.1+0" +version = "0.1.2+0" [[deps.Xorg_libxcb_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "XSLT_jll", "Xorg_libXau_jll", "Xorg_libXdmcp_jll", "Xorg_libpthread_stubs_jll"] -git-tree-sha1 = "bcd466676fef0878338c61e655629fa7bbc69d8e" +git-tree-sha1 = "1a74296303b6524a0472a8cb12d3d87a78eb3612" uuid = "c7cfdc94-dc32-55de-ac96-5a1b8d977c5b" -version = "1.17.0+0" +version = "1.17.0+3" [[deps.Xorg_xtrans_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "e92a1a012a10506618f10b7047e478403a046c77" +git-tree-sha1 = "6dba04dbfb72ae3ebe5418ba33d087ba8aa8cb00" uuid = "c5fb5394-a638-5e4d-96e5-b29de1b5cf10" -version = "1.5.0+0" +version = "1.5.1+0" [[deps.Zlib_jll]] deps = ["Libdl"] @@ -1639,9 +1657,9 @@ version = "1.2.13+1" [[deps.Zstd_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "555d1076590a6cc2fdee2ef1469451f872d8b41b" +git-tree-sha1 = "446b23e73536f84e8037f5dce465e92275f6a308" uuid = "3161d3a3-bdf6-5164-811a-617609db77b4" -version = "1.5.6+1" +version = "1.5.7+1" [[deps.isoband_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Pkg"] @@ -1651,15 +1669,15 @@ version = "0.2.3+0" [[deps.libaec_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "46bf7be2917b59b761247be3f317ddf75e50e997" +git-tree-sha1 = "f5733a5a9047722470b95a81e1b172383971105c" uuid = "477f73a3-ac25-53e9-8cc3-50b2fa2566f0" -version = "1.1.2+0" +version = "1.1.3+0" [[deps.libaom_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "1827acba325fdcdf1d2647fc8d5301dd9ba43a9d" +git-tree-sha1 = "522c1df09d05a71785765d19c9524661234738e9" uuid = "a4ae2306-e953-59d6-aa16-d00cac43593b" -version = "3.9.0+0" +version = "3.11.0+0" [[deps.libass_jll]] deps = ["Artifacts", "Bzip2_jll", "FreeType2_jll", "FriBidi_jll", "HarfBuzz_jll", "JLLWrappers", "Libdl", "Zlib_jll"] @@ -1680,15 +1698,15 @@ version = "2.0.3+0" [[deps.libpng_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Zlib_jll"] -git-tree-sha1 = "b70c870239dc3d7bc094eb2d6be9b73d27bef280" +git-tree-sha1 = "068dfe202b0a05b8332f1e8e6b4080684b9c7700" uuid = "b53b4c65-9356-5827-b1ea-8c7a1a84506f" -version = "1.6.44+0" +version = "1.6.47+0" [[deps.libsixel_jll]] -deps = ["Artifacts", "JLLWrappers", "JpegTurbo_jll", "Libdl", "Pkg", "libpng_jll"] -git-tree-sha1 = "7dfa0fd9c783d3d0cc43ea1af53d69ba45c447df" +deps = ["Artifacts", "JLLWrappers", "JpegTurbo_jll", "Libdl", "libpng_jll"] +git-tree-sha1 = "c1733e347283df07689d71d61e14be986e49e47a" uuid = "075b6546-f08a-558a-be8f-8157d0f608a5" -version = "1.10.3+1" +version = "1.10.5+0" [[deps.libvorbis_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl", "Ogg_jll", "Pkg"] @@ -1698,9 +1716,9 @@ version = "1.3.7+2" [[deps.libwebp_jll]] deps = ["Artifacts", "Giflib_jll", "JLLWrappers", "JpegTurbo_jll", "Libdl", "Libglvnd_jll", "Libtiff_jll", "libpng_jll"] -git-tree-sha1 = "ccbb625a89ec6195856a50aa2b668a5c08712c94" +git-tree-sha1 = "d2408cac540942921e7bd77272c32e58c33d8a77" uuid = "c5f90fcd-3b7e-5836-afba-fc50a0988cb2" -version = "1.4.0+0" +version = "1.5.0+0" [[deps.nghttp2_jll]] deps = ["Artifacts", "Libdl"] @@ -1709,9 +1727,9 @@ version = "1.52.0+1" [[deps.oneTBB_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "7d0ea0f4895ef2f5cb83645fa689e52cb55cf493" +git-tree-sha1 = "d5a767a3bb77135a99e433afe0eb14cd7f6914c3" uuid = "1317d2d5-d96f-522e-a858-c73665f53c3e" -version = "2021.12.0+0" +version = "2022.0.0+0" [[deps.p7zip_jll]] deps = ["Artifacts", "Libdl"] @@ -1720,9 +1738,9 @@ version = "17.4.0+2" [[deps.x264_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] -git-tree-sha1 = "35976a1216d6c066ea32cba2150c4fa682b276fc" +git-tree-sha1 = "14cc7083fc6dff3cc44f2bc435ee96d06ed79aa7" uuid = "1270edf5-f2f9-52d2-97e9-ab00b5d0237a" -version = "10164.0.0+0" +version = "10164.0.1+0" [[deps.x265_jll]] deps = ["Artifacts", "JLLWrappers", "Libdl"] diff --git a/src/REST/Client.jl b/src/REST/Client.jl index 61814f4..1a91483 100644 --- a/src/REST/Client.jl +++ b/src/REST/Client.jl @@ -50,8 +50,8 @@ end function listfiles(tagger::RemoteTagger, srcdir::String) resp = HTTP.get("$(url(tagger, "list-files"))/$srcdir") - @info "listfiles" transcode(String, resp.body) - String[] + resp = transcode(String, resp.body) + return JSON3.read(resp) end function Taggers.pull(tagger::RemoteTagger, destdir::String) @@ -85,7 +85,13 @@ end function Taggers.pushfile(tagger::RemoteTagger, src) request = url(tagger, "push-file") - @info "dummy push-file" src + filename = basename(src) + content = read(src, String) + # emulate curl's behavior + boundary = "------------------------8vna2TYHERnQGhqhQLdlHq" # whatever + headers = [("Content-Type" => "multipart/form-data; boundary=$boundary")] + body = "$boundary\r\nContent-Disposition: form-data; filename=\"$filename\"\r\nContent-Type: application/octet-steam\r\n\r\n$content\r\n$boundary--\r\n" + HTTP.post(request, headers, body) end function Taggers.push(tagger::RemoteTagger, file::String, metadata; clean=true) diff --git a/test/rest_client.sh b/test/rest_client.sh index 23daccb..9763454 100755 --- a/test/rest_client.sh +++ b/test/rest_client.sh @@ -6,6 +6,12 @@ this_script=$(realpath "${BASH_SOURCE[0]}") larvatagger_jl_project_root=$(dirname "$(dirname "${this_script}")") larvatagger_project_root=$(dirname "${larvatagger_jl_project_root}") +if [ -z "$JULIA_VERSION" ]; then + JULIA_VERSION=1.10 +else + echo "Using environment variable: JULIA_VERSION= $JULIA_VERSION" +fi + tagging_backend=MaggotUBA tagging_model=20230311 lt_backend_port=9285 @@ -13,20 +19,23 @@ lt_backend_port=9285 # pre-requisites are similar to rest_server.sh # pre-compile -julia +1.10 --project="${larvatagger_jl_project_root}" -q -e "using LarvaTagger" +julia "+$JULIA_VERSION" --project="${larvatagger_jl_project_root}" -q -e "using LarvaTagger" # run and background the backend server JULIA_PROJECT="${larvatagger_project_root}/TaggingBackends" \ - julia +1.10 --project="${larvatagger_jl_project_root}" -i \ + julia "+$JULIA_VERSION" --project="${larvatagger_jl_project_root}" -i \ -e "using LarvaTagger.REST.Server; run_backend(\"${larvatagger_project_root}\"; port=${lt_backend_port})" & lt_backend_pid=$! # run the frontend server -JULIA="julia +1.10" ${larvatagger_jl_project_root}/scripts/larvatagger-gui.jl http://localhost:${lt_backend_port} +JULIA="julia +$JULIA_VERSION" ${larvatagger_jl_project_root}/scripts/larvatagger-gui.jl http://localhost:${lt_backend_port} # scenarii: # * click on "Autotag" prior to loading any files (if not disabled, as with a bug in v0.19) -# * load a tracking data file, and then click on "Autotag" +# * load a tracking data file, and then click on "Autotag"; +# expected: a predicted.label is generated and the GUI reloads +# * load a second tracking data file (binary if first was ascii or vice versa), select another model instance, click again on "Autotag"; +# expected: a new token was issued + similar outcome as previous step, with tracking data file and tagging model properly identified in the predicted.label file kill $lt_backend_pid wait $lt_backend_pid -- GitLab From a83df5d3d76c0cef7cae402a7216d2d71d60e0b5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=C3=A7ois=20Laurent?= <francois.laurent@posteo.net> Date: Mon, 31 Mar 2025 15:35:45 +0200 Subject: [PATCH 4/8] new install defaults --- Manifest-v1.11.toml | 4 +-- Manifest.toml | 4 +-- scripts/install.sh | 81 +++++++++++++++++++++++++++++++++++++++++---- 3 files changed, 79 insertions(+), 10 deletions(-) diff --git a/Manifest-v1.11.toml b/Manifest-v1.11.toml index 4a3fd72..0aa18a8 100644 --- a/Manifest-v1.11.toml +++ b/Manifest-v1.11.toml @@ -997,11 +997,11 @@ version = "1.2.0" [[deps.NyxWidgets]] deps = ["Bonito", "Colors", "Format", "LazyArtifacts", "Observables"] -git-tree-sha1 = "d5addf940e4265b3ca2a6fe29b8ff24bf3b13b98" +git-tree-sha1 = "cdc029870ac2ab9522e700f3e2b3209b33389fa4" repo-rev = "main" repo-url = "https://gitlab.com/dbc-nyx/NyxWidgets.jl" uuid = "c288fd06-43d3-4b04-8307-797133353e2e" -version = "0.2.1" +version = "0.2.2" [[deps.Observables]] git-tree-sha1 = "7438a59546cf62428fc9d1bc94729146d37a7225" diff --git a/Manifest.toml b/Manifest.toml index 5b90db9..ddca19f 100644 --- a/Manifest.toml +++ b/Manifest.toml @@ -985,11 +985,11 @@ version = "1.2.0" [[deps.NyxWidgets]] deps = ["Bonito", "Colors", "Format", "LazyArtifacts", "Observables"] -git-tree-sha1 = "d5addf940e4265b3ca2a6fe29b8ff24bf3b13b98" +git-tree-sha1 = "cdc029870ac2ab9522e700f3e2b3209b33389fa4" repo-rev = "main" repo-url = "https://gitlab.com/dbc-nyx/NyxWidgets.jl" uuid = "c288fd06-43d3-4b04-8307-797133353e2e" -version = "0.2.1" +version = "0.2.2" [[deps.Observables]] git-tree-sha1 = "7438a59546cf62428fc9d1bc94729146d37a7225" diff --git a/scripts/install.sh b/scripts/install.sh index a1a2b1d..d649e46 100755 --- a/scripts/install.sh +++ b/scripts/install.sh @@ -1,5 +1,38 @@ #!/usr/bin/env bash +for flag in "$@"; do + if [ "$flag" = "-h" -o "$flag" = "--help" ]; then + echo "Command-line installer for LarvaTagger" + echo + echo "Usage:" + echo " $0" + echo " WITH_BACKEND=1 $0" + echo " WITH_BACKEND=1 $0 --legacy" + echo " $0 --with-default-backend" + echo " $0 --with-backend --legacy" + echo " $0 --uninstall" + echo " $0 --help" + echo + echo "The legacy installation path for the MaggotUBA-based tagger relies" + echo "on Python3.8 and Torch1." + echo "The current default relies on Python3.11 and Torch2." + echo "Other environment variables can be set, similarly to WITH_BACKEND," + echo "to control the script's behavior:" + echo " variable default value" + echo " BIN_DIR ~/.local/bin" + echo " LARVATAGGER_PATH ~/.local/share/larvatagger" + echo " JULIA_CHANNEL lts" + echo " JULIA_VERSION 1.10" + echo " PYTHON_VERSION 3.11 (3.8 if --legacy)" + echo " MAGGOTUBA_CORE_BRANCH main" + echo " MAGGOTUBA_ADAPTER_BRANCH torch2 (main if --legacy)" + echo " TAGGINGBACKENDS_BRANCH main" + echo " PLANARLARVAE_BRANCH main" + echo " LARVATAGGER_BRANCH main" + exit 0 + fi +done + [ -d "`pwd`" ] || cd if [ -z "$BIN_DIR" ]; then @@ -41,28 +74,47 @@ if [ "$1" = "--uninstall" ]; then fi else +# former default: PYTHON_VERSION=3.8 + # the internal_<VAR> variables need to be set non-empty only if # the corresponding <VAR> variable is non-empty; they are used to # determine whether or not to report externally sourced variables internal_WITH_BACKEND= internal_MAGGOTUBA_ADAPTER_BRANCH= internal_MAGGOTUBA_ADAPTER_FREE_DEPENDENCIES= +internal_LEGACY= +internal_WITH_DEFAULT_BACKEND= + +# primary use cases: +# WITH_BACKEND=1 scripts/install.sh +# WITH_BACKEND=1 scripts/install.sh --legacy +# scripts/install.sh --with-default-backend +# scripts/install.sh --with-backend +# scripts/install.sh --with-backend --experimental +# scripts/install.sh --with-backend --legacy + for arg in "$@"; do if [ "$arg" = "--with-default-backend" ]; then WITH_BACKEND=1 internal_WITH_BACKEND=1 - MAGGOTUBA_CORE_BRANCH= - MAGGOTUBA_ADAPTER_BRANCH= + internal_WITH_DEFAULT_BACKEND=1 + if [ "$internal_LEGACY" = "1" ]; then + echo "Ignoring --legacy; pass --with-backend --legacy instead" + internal_LEGACY=0 + fi break elif [ "$arg" = "--with-backend" ]; then WITH_BACKEND=1 internal_WITH_BACKEND=1 elif [ "$arg" = "--experimental" ]; then + echo "The --experimental flag is deprecated and is now default" + internal_LEGACY=0 + elif [ "$arg" = "--legacy" ]; then + internal_LEGACY=1 MAGGOTUBA_CORE_BRANCH= - MAGGOTUBA_ADAPTER_BRANCH=torch2 - internal_MAGGOTUBA_ADAPTER_BRANCH=1 - PYTHON_VERSION=3.11 + # former default (empty) falls back to main + MAGGOTUBA_ADAPTER_BRANCH= elif [ "$arg" = "--free-python-dependencies" ]; then internal_MAGGOTUBA_ADAPTER_FREE_DEPENDENCIES=1 elif [ "$arg" = "--lock-python-dependencies" ]; then @@ -70,6 +122,23 @@ for arg in "$@"; do fi done +if [ "$WITH_BACKEND" = "1" -a "$internal_LEGACY" = "0" ]; then + # new defaults (formerly "--experimental") + MAGGOTUBA_CORE_BRANCH= + MAGGOTUBA_ADAPTER_BRANCH=torch2 + internal_MAGGOTUBA_ADAPTER_BRANCH=1 + PYTHON_VERSION=3.11 +elif [ "$internal_LEGACY" != "1" ]; then + if [ "$internal_WITH_DEFAULT_BACKEND" = "1" ]; then + echo "The Python3.11/Torch2 backend is now default" + echo "Pass flags --with-backend --legacy to select the former Python3.8/Torch1 backend" + fi + MAGGOTUBA_CORE_BRANCH= + MAGGOTUBA_ADAPTER_BRANCH=torch2 + internal_MAGGOTUBA_ADAPTER_BRANCH=1 + PYTHON_VERSION=3.11 +fi + PYTHON="python$PYTHON_VERSION" check_brew() { @@ -266,7 +335,7 @@ if [ -d LarvaTagger.jl ]; then echo "LarvaTagger.jl installation found; skipping" else if [ -z "$LARVATAGGER_BRANCH" ]; then - LARVATAGGER_BRANCH=dev + LARVATAGGER_BRANCH=main else echo "Using environment variable: LARVATAGGER_BRANCH= $LARVATAGGER_BRANCH" fi -- GitLab From e77dd8a5993fee6200e6d6f1d51fe528b87fcae4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=C3=A7ois=20Laurent?= <francois.laurent@posteo.net> Date: Tue, 1 Apr 2025 12:58:38 +0200 Subject: [PATCH 5/8] feat: tooltip text for tagging backends and taggers --- README.md | 9 ++--- recipes/Dockerfile | 5 ++- recipes/Dockerfile.local | 20 ++++++---- recipes/Dockerfile.pasteurjanelia | 3 +- recipes/patch.sh | 62 +++++++++++++++++++++++++++++++ scripts/larvatagger.sh | 54 +++++++++++++++++++++++---- src/REST/Client.jl | 17 ++++++++- src/REST/Model.jl | 51 ++++++++++++++++++------- src/larvatagger.js | 13 +++++-- src/wgl.jl | 14 +++++-- test/rest_server.sh | 32 +++++----------- 11 files changed, 209 insertions(+), 71 deletions(-) create mode 100755 recipes/patch.sh diff --git a/README.md b/README.md index 9996377..6f7173b 100644 --- a/README.md +++ b/README.md @@ -111,15 +111,12 @@ curl -sSL "https://gitlab.pasteur.fr/nyx/larvatagger.jl/-/raw/dev/scripts/instal ``` In the latter case, the script may install several extra dependencies, but not all of them. -In particular, Python is required; either 3.8 with `--with-default-backend`, or 3.11 with `--with-backend --experimental`. +In particular, Python is required; either 3.11 with `--with-default-backend`, or 3.8 with `--with-backend --legacy`. If `pyenv` is available, the script will use this tool to install Python. -Otherwise, `python3.8` and `python3.8-venv` may have to be manually installed. +Otherwise, `python3.11` and `python3.11-venv` may have to be manually installed. On WSL, the script will attempt to install `pyenv` and Python (tested with Ubuntu 20.04). -On macOS, the full LarvaTagger suite can be installed only with the `--with-backend --experimental` options: -``` -curl -sSL "https://gitlab.pasteur.fr/nyx/larvatagger.jl/-/raw/dev/scripts/install.sh?ref_type=heads&inline=false" | /bin/bash -s -- --with-backend --experimental -``` +On macOS, the full LarvaTagger suite can be installed only with the default options (`--legacy` is not supported). This script can also uninstall LarvaTagger (if installed with the same script) with: `curl -sSL "https://gitlab.pasteur.fr/nyx/larvatagger.jl/-/raw/dev/scripts/install.sh?ref_type=heads&inline=false" | /bin/bash -s -- --uninstall` which can be useful for example prior to reinstalling after failure. diff --git a/recipes/Dockerfile b/recipes/Dockerfile index 11d0e1c..b83d356 100644 --- a/recipes/Dockerfile +++ b/recipes/Dockerfile @@ -1,4 +1,4 @@ -FROM julia:1.10.8-bullseye AS base +FROM julia:1.10.9-bullseye AS base ARG PROJECT_DIR=/app ARG BRANCH=main @@ -82,7 +82,8 @@ RUN if [ -z $TAGGINGBACKENDS_BRANCH ]; then \ && poetry add "pynvml==11.4.1" \ && if [ "$(echo $BACKEND | cut -d/ -f2)" = "main" ] || [ "$(echo $BACKEND | cut -d/ -f2)" = "dev" ]; then \ julia -e 'using Pkg; Pkg.add("JSON3")' \ - && scripts/make_models.jl default; \ + && scripts/make_models.jl default \ + && recipes/patch.sh; \ fi \ && rm -rf ~/.cache; \ fi diff --git a/recipes/Dockerfile.local b/recipes/Dockerfile.local index 5d03313..34d31fc 100644 --- a/recipes/Dockerfile.local +++ b/recipes/Dockerfile.local @@ -1,30 +1,31 @@ # To be built with scripts/larvatagger.sh build --dev -FROM julia:1.8.2-bullseye +FROM julia:1.10.9-bullseye ENV JULIA_PROJECT=/app/TaggingBackends ENV JULIA_DEPOT_PATH=/usr/local/share/julia ENV POETRY_VIRTUALENVS_PATH=/usr/local/share/poetry # We assume: -# * current directory name is LarvaTagger; contains the LarvaTagger.jl project; -# * PlanarLarvae.jl project is available as sibling directory PlanarLarvae; +# * current directory name is LarvaTagger.jl; contains the LarvaTagger.jl project; +# * PlanarLarvae.jl project is available as sibling directory PlanarLarvae.jl; # * TaggingBackends project is available as sibling directory TaggingBackends; # * MaggotUBA-core project is available as sibling directory MaggotUBA-core; # * MaggotUBA-adapter project is available as sibling directory MaggotUBA-adapter. # Paths are given relative to parent directory, since larvatagger.sh will move 1 level up # prior to calling docker build -ARG PLANARLARVAE=./PlanarLarvae -ARG LARVATAGGER=./LarvaTagger +ARG PLANARLARVAE=./PlanarLarvae.jl +ARG LARVATAGGER=./LarvaTagger.jl ARG TAGGINGBACKENDS=./TaggingBackends ARG MAGGOTUBA_CORE=./MaggotUBA-core ARG MAGGOTUBA_ADAPTER=./MaggotUBA-adapter COPY $PLANARLARVAE/src /app/PlanarLarvae/src -COPY $PLANARLARVAE/Project.toml $PLANARLARVAE/Manifest.toml /app/PlanarLarvae/ +COPY $PLANARLARVAE/Project.toml $PLANARLARVAE/Manifest.toml* /app/PlanarLarvae/ COPY $LARVATAGGER/src /app/src COPY $LARVATAGGER/scripts /app/scripts +COPY $LARVATAGGER/recipes/patch.sh /app/recipes/ COPY $LARVATAGGER/Project.toml $LARVATAGGER/Manifest.toml /app/ RUN apt-get update \ @@ -43,7 +44,8 @@ COPY $MAGGOTUBA_CORE/src /app/MaggotUBA-core/src COPY $MAGGOTUBA_CORE/pyproject.toml /app/MaggotUBA-core/ COPY $MAGGOTUBA_ADAPTER/src /app/MaggotUBA/src COPY $MAGGOTUBA_ADAPTER/pyproject.toml /app/MaggotUBA/ -COPY $MAGGOTUBA_ADAPTER/models/20221005 /app/MaggotUBA/models/20221005 +COPY $MAGGOTUBA_ADAPTER/models/20230311 /app/MaggotUBA/models/20230311 +COPY $MAGGOTUBA_ADAPTER/models/20230311-0 /app/MaggotUBA/models/20230311-0 COPY $MAGGOTUBA_ADAPTER/pretrained_models/default /app/MaggotUBA/pretrained_models/default RUN python3 -m pip install poetry \ @@ -54,6 +56,8 @@ RUN python3 -m pip install poetry \ && cd /app/MaggotUBA \ && poetry add ../MaggotUBA-core \ && poetry add ../TaggingBackends \ - && poetry install + && poetry install \ + && cd /app \ + && recipes/patch.sh ENTRYPOINT ["larvatagger.jl"] diff --git a/recipes/Dockerfile.pasteurjanelia b/recipes/Dockerfile.pasteurjanelia index 6492460..cdb79e2 100644 --- a/recipes/Dockerfile.pasteurjanelia +++ b/recipes/Dockerfile.pasteurjanelia @@ -27,5 +27,6 @@ RUN cd $PROJECT_DIR \ && make package \ && rm -rf bin/matlab/2023b/bin/glnxa64/matlab_startup_plugins/matlab_graphics_ui \ && rm -rf bin/matlab/2023b/bin/glnxa64/matlab_startup_plugins/foundation/platform/pf_matlab_integ \ - && rm -rf .git ~/.cache + && rm -rf .git ~/.cache \ + && cd .. && recipes/patch.sh diff --git a/recipes/patch.sh b/recipes/patch.sh new file mode 100755 index 0000000..b32d491 --- /dev/null +++ b/recipes/patch.sh @@ -0,0 +1,62 @@ +#!/bin/sh + +# patch the taggers in a Docker image so that they include metadata.json files + +if [ -d "MaggotUBA" ]; then + if ! [ -f "MaggotUBA/metadata.json" ]; then + cat <<"EOF" >MaggotUBA/metadata.json +{ + "name": "MaggotUBA", + "homepage": "https://gitlab.pasteur.fr/nyx/MaggotUBA-adapter", + "description": "Action classifiers based on MaggotUBA encoders" +} +EOF + fi + + dir="MaggotUBA/models/20230311" + if [ -d "$dir" ] && ! [ -f "$dir/metadata.json" ]; then + cat <<"EOF" >$dir/metadata.json +{ + "name": "20230311", + "homepage": "https://gitlab.pasteur.fr/nyx/MaggotUBA-adapter#20230311-0-and-20230311", + "description": "Tagger trained on t15 to emulate JBM's tagger on the 7-behavior classification task" +} +EOF + fi + + dir="MaggotUBA/models/20230311-0" + if [ -d "$dir" ] && ! [ -f "$dir/metadata.json" ]; then + cat <<"EOF" >$dir/metadata.json +{ + "name": "20230311-0", + "homepage": "https://gitlab.pasteur.fr/nyx/MaggotUBA-adapter#20230311-0-and-20230311", + "description": "Tagger trained on t15 to emulate JBM's tagger on the 12-behavior classification task" +} +EOF + fi + +fi + +if [ -d "PasteurJanelia" ]; then + if ! [ -f "PasteurJanelia/metadata.json" ]; then + cat <<"EOF" >PasteurJanelia/metadata.json +{ + "name": "PasteurJanelia", + "homepage": "https://gitlab.pasteur.fr/nyx/PasteurJanelia-adapter", + "description": "Action classifiers initially designed by JBM at Janelia" +} +EOF + fi + + dir="PasteurJanelia/models/5layers" + if [ -d "$dir" ] && ! [ -f "$dir/metadata.json" ]; then + cat <<"EOF" >$dir/metadata.json +{ + "name": "5layers", + "homepage": "https://gitlab.pasteur.fr/nyx/PasteurJanelia-adapter", + "description": "JBM's final tagger for use on the t2 and t7 trackers" +} +EOF + fi + +fi diff --git a/scripts/larvatagger.sh b/scripts/larvatagger.sh index 3cf76b9..ff32aec 100755 --- a/scripts/larvatagger.sh +++ b/scripts/larvatagger.sh @@ -2,7 +2,7 @@ for _ in $(seq $#); do case $1 in - open|import|merge|train|predict|-V|--version|--more-help|reverse-mapping|confusion) + open|import|merge|train|predict|-V|--version|--more-help|reverse-mapping|confusion|backend) cmd=$1 shift break @@ -102,6 +102,15 @@ done if [ -z "$no_cache" ] && [ -z "$cache" ]; then DOCKER_ARGS="--no-cache $DOCKER_ARGS" fi + +if [ "$BUILD" == "--dev" ]; then +if ! [[ "$LARVATAGGER_IMAGE" == *:* ]]; then LARVATAGGER_IMAGE="${LARVATAGGER_IMAGE}:dev"; fi +PROJECT_ROOT=$(basename $(pwd)) +cd .. +echo "DOCKER_BUILDKIT=1 $docker build -t \"$LARVATAGGER_IMAGE\" -f \"$PROJECT_ROOT/recipes/Dockerfile.local\" ${DOCKER_ARGS}." +DOCKER_BUILDKIT=1 $docker build -t "$LARVATAGGER_IMAGE" -f "$PROJECT_ROOT/recipes/Dockerfile.local" ${DOCKER_ARGS}. +else + if [ -z "$target" ]; then DOCKER_ARGS="--target $TARGET $DOCKER_ARGS" fi @@ -111,19 +120,16 @@ else echo "Using environment variable DOCKERFILE= $DOCKERFILE" fi DOCKER_ARGS="-f \"$DOCKERFILE\" $DOCKER_ARGS" -if [ "$BUILD" == "--dev" ]; then -if ! [[ "$LARVATAGGER_IMAGE" == *:* ]]; then LARVATAGGER_IMAGE="${LARVATAGGER_IMAGE}:dev"; fi -PROJECT_ROOT=$(basename $(pwd)) -cd .. -DOCKER_BUILDKIT=1 $docker build -t "$LARVATAGGER_IMAGE" -f "$PROJECT_ROOT/recipes/Dockerfile.local" ${DOCKER_ARGS}. -elif [ "$BUILD" == "--stable" ]; then + +if [ "$BUILD" == "--stable" ]; then if ! [[ "$LARVATAGGER_IMAGE" == *:* ]]; then LARVATAGGER_IMAGE="${LARVATAGGER_IMAGE}:stable"; fi $docker build -t "$LARVATAGGER_IMAGE" ${DOCKER_ARGS}. else + if ! [[ "$LARVATAGGER_IMAGE" == *:* ]]; then LARVATAGGER_IMAGE="${LARVATAGGER_IMAGE}:latest"; fi if [ -z "$LARVATAGGER_BRANCH" ]; then if [ -z "$LARVATAGGER_DEFAULT_BRANCH" ]; then - LARVATAGGER_BRANCH=dev; + LARVATAGGER_BRANCH=dev else echo "Deprecation notice: LARVATAGGER_DEFAULT_BRANCH has been renamed LARVATAGGER_BRANCH" LARVATAGGER_BRANCH=$LARVATAGGER_DEFAULT_BRANCH @@ -141,6 +147,7 @@ DOCKER_BUILD="$docker build -t "$LARVATAGGER_IMAGE" ${DOCKER_ARGS}--build-arg BR echo $DOCKER_BUILD eval $DOCKER_BUILD fi +fi ;; open) @@ -174,6 +181,34 @@ done DOCKER_RUN="exec $docker run $RUN_ARGS -i ${DOCKER_ARGS}\"$LARVATAGGER_IMAGE\" open \"/data/$file\" $TAGGER_ARGS $@" echo $DOCKER_RUN eval $DOCKER_RUN +;; + + backend) + +if [ -z "$LARVATAGGER_PORT" ]; then +LARVATAGGER_PORT=9285 +elif [ "$LARVATAGGER_PORT" != "9285" ]; then +echo "Using environment variable: LARVATAGGER_PORT= $LARVATAGGER_PORT" +fi +DOCKER_ARGS="-p $LARVATAGGER_PORT:$LARVATAGGER_PORT $DOCKER_ARGS" + +# undocumented feature (copied-pasted from open) +backend=MaggotUBA +while [ -n "$1" -a "$1" = "--external-instance" ]; do +instance=$2; shift 2 +if ! command -v realpath &>/dev/null; then +echo "realpath: command not found" +echo "on macOS: brew install coreutils" +exit 1 +fi +RUN_ARGS="$RUN_ARGS --mount type=bind,src=\"$(realpath $instance)\",dst=/app/$backend/models/$(basename $instance)" +done + +RUN_ARGS="$RUN_ARGS --entrypoint=julia" + +DOCKER_RUN="exec $docker run $RUN_ARGS -i ${DOCKER_ARGS}\"$LARVATAGGER_IMAGE\" $@ --project=/app -e 'using LarvaTagger.REST.Server; run_backend(\"/app\"; port=$LARVATAGGER_PORT, host=\"0.0.0.0\")'" +echo $DOCKER_RUN +eval $DOCKER_RUN ;; import | merge) @@ -371,6 +406,7 @@ Usage: $0 build [--stable] [--with-default-backend] [--with-backend <backend>] $0 confusion <datarepository> $0 merge <filepath> [<outputfilename>] [...] $0 reverse-mapping <filepath> <filename> <outputfilename> + $0 backend $0 --more-help $0 --version $0 --update @@ -390,6 +426,8 @@ the second one with unmapped labels. It generates a third label file with demapp from the first file. This is useful when the first file diverges from the second one by some manual editions, on top of label mapping. +The backend command runs a LarvaTagger's REST server that listens to port 9285 per default. + See --more-help for more information about additional arguments for the other commands from larvatagger.jl. EOT diff --git a/src/REST/Client.jl b/src/REST/Client.jl index 1a91483..611608e 100644 --- a/src/REST/Client.jl +++ b/src/REST/Client.jl @@ -209,11 +209,24 @@ end listmodels(back::LTBackend) = listmodels(back, Val(false)) -listmodels(back::LTBackend, ::Val{false}) = collect(keys(back.taggers)) +function listmodels(back::LTBackend, ::Val{false}) + [OrderedDict("name" => name, + "description" => get(back.metadata[name], :description, ""), + "homepage" => get(back.metadata[name], :homepage, ""), + ) for name in keys(back.taggers)] +end function listmodels(back::LTBackend, ::Val{true}) map(back.active_tagging_backend) do tagging_backend - isnothing(tagging_backend) ? String[] : collect(keys(back.taggers[tagging_backend])) + models = OrderedDict{String, String}[] + for name in keys(back.taggers[tagging_backend]) + metadata = back.metadata[tagging_backend][:models][name] + push!(models, OrderedDict("name" => name, + "description" => get(metadata, :description, ""), + "homepage" => get(metadata, :homepage, ""), + )) + end + return models end end diff --git a/src/REST/Model.jl b/src/REST/Model.jl index 781ce7a..9effac9 100644 --- a/src/REST/Model.jl +++ b/src/REST/Model.jl @@ -187,26 +187,49 @@ function pullfile(lt_backend, backend_dir, model_instance, token, filename) return HTTP.Response(200, header, body) end +function loadmodel(dir, hasinstances=false) + metadata = nothing + for filename in ("metadata", "metadata.json") + if isfile(joinpath(dir, filename)) + metadata = JSON3.read(joinpath(dir, filename)) + break + end + end + name = basename(dir) + T = if hasinstances + Union{AbstractString, Vector{OrderedDict{AbstractString, AbstractString}}} + else + AbstractString + end + model = OrderedDict{AbstractString, T}( + "name" => name, + "description" => "", + "homepage" => "", + ) + if !isnothing(metadata) + for key in keys(model) + key′ = Symbol(key) + if haskey(metadata, key′) + model[key] = metadata[key′] + end + end + end + return model +end + function listtaggers(lt_backend) inventory = Vector{OrderedDict{String, Any}}() backends_dir = lt_backend.root[] - for tagging_backend in readdir(backends_dir) - tagging_backend_path = joinpath(backends_dir, tagging_backend) + for tagging_backend_path in readdir(backends_dir; join=true) Taggers.isbackend(tagging_backend_path) || continue models_dir = joinpath(tagging_backend_path, "models") - models = [OrderedDict( - "name" => dir, - "description" => "", - "homepage" => "", - ) for dir in readdir(models_dir) if isdir(joinpath(models_dir, dir))] - push!(inventory, OrderedDict( - "name" => tagging_backend, - "description" => "", - "homepage" => "", - "models" => models, - )) + models = loadmodel.(readdir(models_dir; join=true)) + isempty(models) && continue + tagging_backend = loadmodel(tagging_backend_path, true) + tagging_backend["models"] = models + push!(inventory, tagging_backend) end - return JSON3.write(inventory) + return JSON3.write(unique(inventory)) end function predict(lt_backend, backend_dir, model_instance, token) diff --git a/src/larvatagger.js b/src/larvatagger.js index d65fb7d..8437424 100644 --- a/src/larvatagger.js +++ b/src/larvatagger.js @@ -132,12 +132,17 @@ const LarvaTagger = (function () { selectElement.remove(0); } for (let i = 0; i < selectOptions.length; i++) { - const option = document.createElement('option'); - option.value = selectOptions[i]; - option.text = selectOptions[i]; + let option = document.createElement('option'), + name = selectOptions[i]; + if (typeof name === 'object') { + option.title = name['description']; + name = name['name']; + } + option.value = name; + option.text = name; if (jlObserver !== undefined) { option.ondblclick = () => { - jlObserver.notify(selectOptions[i]); + jlObserver.notify(name); }; } selectElement.append(option); diff --git a/src/wgl.jl b/src/wgl.jl index 6674dc5..2579cac 100644 --- a/src/wgl.jl +++ b/src/wgl.jl @@ -1001,17 +1001,25 @@ function backendmenu(controller, location) BackendMenu(backends, models, send2backend, dom_id()) end +function lowermodel(model) + if model isa AbstractString + DOM.option(model; value=model) + else + name = model["name"] + DOM.option(name; value=name, title=model["description"]) + end +end + function lowerdom(bs::BackendMenu) model_instance = get_model_instance(bs.backends) update_model_instance = js"(evt)=>{ $model_instance.notify(evt.srcElement.value); }" - select_dom = DOM.select(DOM.option(model; value=model) for model in bs.models[]; + select_dom = DOM.select(lowermodel.(bs.models[]); onchange=update_model_instance, class=css_button) active_backend = get_active_backend(bs.backends) update_active_backend = js"(evt)=>{ $active_backend.notify(evt.srcElement.value); }" return DOM.div(DOM.label("Backend"), - DOM.select(DOM.option(backend; value=backend) - for backend in get_backend_names(bs.backends); + DOM.select(lowermodel.(get_backend_names(bs.backends)); onchange=update_active_backend, class=css_button), DOM.label("Model instance"), diff --git a/test/rest_server.sh b/test/rest_server.sh index 6de171f..d69c186 100755 --- a/test/rest_server.sh +++ b/test/rest_server.sh @@ -12,7 +12,7 @@ lt_backend_port=9285 # assumed directory structure: # the MaggotUBA-adapter, TaggingBackends, NyxArtefacts and LarvaTagger.jl projects are siblings in the ${larvatagger_project_root} directory; -# the MaggotUBA-adapter project is available both as directory MaggotUBA-adapter and link MaggotUBA (${tagging_backend}); +# the MaggotUBA-adapter project is available both as directory MaggotUBA (${tagging_backend}); # the MaggotUBA-adapter tagging backend contains two trained models (or model instances): 20230311 and 20230311-0; # the NyxArtefacts project is available as directory Artefacts; # MaggotUBA is installed with JULIA_PROJECT pointing at the TaggingBackends directory @@ -113,32 +113,18 @@ else fi # discover the backend(s) and their models -discovered_backends=`curl -sS http://localhost:${lt_backend_port}/list-backends` - -backend_metadata() { - local desc1= - local link1= - local desc2= - local link2= - local desc3= - local link3= - echo "{\"name\":\"$1\",\"description\":\"$desc1\",\"homepage\":\"$link1\",\"models\":[{\"name\":\"20230311\",\"description\":\"$desc2\",\"homepage\":\"$link2\"},{\"name\":\"20230311-0\",\"description\":\"$desc3\",\"homepage\":\"$link3\"}]}" -} -expected_backends="[`backend_metadata $tagging_backend`,`backend_metadata ${tagging_backend}-adapter`]" +discovered_taggers=`curl -sS http://localhost:${lt_backend_port}/list-taggers` + +expected_taggers="[{\"name\":\"MaggotUBA\",\"description\":\"Action classifiers based on MaggotUBA encoders\",\"homepage\":\"https://gitlab.pasteur.fr/nyx/MaggotUBA-adapter\",\"models\":[{\"name\":\"20230311\",\"description\":\"Tagger trained on t15 to emulate JBM's tagger on the 7-behavior classification task\",\"homepage\":\"https://gitlab.pasteur.fr/nyx/MaggotUBA-adapter#20230311-0-and-20230311\"},{\"name\":\"20230311-0\",\"description\":\"Tagger trained on t15 to emulate JBM's tagger on the 12-behavior classification task\",\"homepage\":\"https://gitlab.pasteur.fr/nyx/MaggotUBA-adapter#20230311-0-and-20230311\"}]}]" -if [ "$discovered_backends" = "$expected_backends" ]; then - echo "list-backends: success" +if [ "$discovered_taggers" = "$expected_taggers" ]; then + echo "list-taggers: success" else - echo "list-backends: failure" + echo "list-taggers: failure" echo "expected:" - echo "$expected_backends" + echo "$expected_taggers" echo "got:" - echo "$discovered_backends" - # further diagnose - model_instances=(`ls "${larvatagger_project_root}/${tagging_backend}/models"`) - if ! [ ${#model_instances[@]} -eq 2 -a "${model_instances[0]}" = "20230311" -a "${model_instances[1]}" = "20230311-0" ]; then - echo "tagging backend is not adequately set up" - fi + echo "$discovered_taggers" fi cp "${larvatagger_jl_project_root}"/20140805_101522@FCF_attP2_1500062@UAS_TNT_2_0003@t5@p_8_45s1x30s0s#p_8_105s10x2s10s#n#n@100.* "${larvatagger_project_root}/${tagging_backend}/data/raw/${token}/" -- GitLab From 52c7016ec4f9404427866541f4332b52f0ac1730 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=C3=A7ois=20Laurent?= <francois.laurent@posteo.net> Date: Wed, 2 Apr 2025 13:26:27 +0200 Subject: [PATCH 6/8] feat: Taggers.apply_make_dataset, make_dataset metadata entry, version increment --- Project.toml | 2 +- doc/develop.md | 38 ++++++++++++++++++++++++- recipes/Dockerfile | 1 + recipes/patch.sh | 11 ++++++-- scripts/install.sh | 4 +-- src/REST/Client.jl | 7 +++-- src/REST/Model.jl | 42 +++++----------------------- src/Taggers.jl | 61 +++++++++++++++++++++++++++++++++++++++-- src/backends.jl | 4 +-- test/deploy_and_test.sh | 4 +-- 10 files changed, 124 insertions(+), 50 deletions(-) diff --git a/Project.toml b/Project.toml index 4707dab..82ad0ca 100644 --- a/Project.toml +++ b/Project.toml @@ -1,7 +1,7 @@ name = "LarvaTagger" uuid = "8b3b36f1-dfed-446e-8561-ea19fe966a4d" authors = ["François Laurent", "Institut Pasteur"] -version = "0.19.1" +version = "0.20" [deps] Bonito = "824d6782-a2ef-11e9-3a09-e5662e0c26f8" diff --git a/doc/develop.md b/doc/develop.md index ec368bc..6648bcc 100644 --- a/doc/develop.md +++ b/doc/develop.md @@ -22,4 +22,40 @@ On the *Julia* side, the lower-level functionalities are provided by the *Planar Similarly, the *TidyObservables.jl* project has unit tests and a GitLab workflow to run these tests on every commit. For the remaining part of the *LarvaTagger* project, high-level functional tests only are available. -These tests are available in the *LarvaTagger.jl* project, in the test directory, file *scenarii.sh*. They depend on [*shUnit2*](https://github.com/kward/shunit2). +These tests are available in the *LarvaTagger.jl* project, as file `test/deploy_and_test.sh`. They depend on [*shUnit2*](https://github.com/kward/shunit2). + +The `test/deploy_and_test.sh` script implicitly tests the `scripts/install.sh` script, and then runs the `test/scenarii.sh` script. +The `test/scenarii.sh` script requires some test data that are downloaded by the `test/deploy_and_test.sh` script. +If these test data cannot be fetched, please contact François Laurent so that the data are made available again (the download link periodically expires). + +## REST + +The REST API can be tested running the `test/rest_server.sh` and `test/rest_client.sh` scripts. + +The `test/rest_server.sh` script is fully automatic and completes with a stack trace that results from killing the backend after the last test. + +The `test/rest_client.sh` script does not perform any actual test. +It launches a backend and a frontend, and the user is expected to manually operate the frontend to test the communication between the backend and the frontend. + +## Docker images + +The most complete test image can be built as follows: + +``` +docker=docker LARVATAGGER_IMAGE=flaur/larvatagger:latest scripts/larvatagger.sh build --dev +docker build -t larvatagger:bigfat -f recipes/Dockerfile.pasteurjanelia . +``` + +Subsequent tests will run the backend using `larvatagger:bigfat` image: +``` +docker=docker LARVATAGGER_IMAGE="larvatagger:bigfat" scripts/larvatagger.sh backend +``` + +The frontend is more conveniently run from the source tree: +``` +scripts/larvatagger-gui.jl http://localhost:9285 +``` + +The `docker=docker` environment variable is required if command `podman` is available. +The `scripts/larvatagger.sh` script falls back on using `podman` instead of `docker`, if `podman` is available, but it is recommended to perform tests using Docker. +In addition, at present, building the image works with Docker buildx only. diff --git a/recipes/Dockerfile b/recipes/Dockerfile index b83d356..c4d6989 100644 --- a/recipes/Dockerfile +++ b/recipes/Dockerfile @@ -83,6 +83,7 @@ RUN if [ -z $TAGGINGBACKENDS_BRANCH ]; then \ && if [ "$(echo $BACKEND | cut -d/ -f2)" = "main" ] || [ "$(echo $BACKEND | cut -d/ -f2)" = "dev" ]; then \ julia -e 'using Pkg; Pkg.add("JSON3")' \ && scripts/make_models.jl default \ + && cd $PROJECT_DIR \ && recipes/patch.sh; \ fi \ && rm -rf ~/.cache; \ diff --git a/recipes/patch.sh b/recipes/patch.sh index b32d491..42da07a 100755 --- a/recipes/patch.sh +++ b/recipes/patch.sh @@ -1,6 +1,7 @@ #!/bin/sh -# patch the taggers in a Docker image so that they include metadata.json files +# patch the taggers in a Docker image so that they include metadata.json files; +# ultimately the taggers should manage their metadata.json files themselves. if [ -d "MaggotUBA" ]; then if ! [ -f "MaggotUBA/metadata.json" ]; then @@ -37,13 +38,19 @@ EOF fi +# note about make_dataset: +# * default is equivalent to "train, finetune" +# * can be "always" or a comma-separated list of processing steps +# * valid steps are "train", "finetune", "predict", "embed" + if [ -d "PasteurJanelia" ]; then if ! [ -f "PasteurJanelia/metadata.json" ]; then cat <<"EOF" >PasteurJanelia/metadata.json { "name": "PasteurJanelia", "homepage": "https://gitlab.pasteur.fr/nyx/PasteurJanelia-adapter", - "description": "Action classifiers initially designed by JBM at Janelia" + "description": "Action classifiers initially designed by JBM at Janelia", + "make_dataset": "always" } EOF fi diff --git a/scripts/install.sh b/scripts/install.sh index d649e46..30f8023 100755 --- a/scripts/install.sh +++ b/scripts/install.sh @@ -180,7 +180,7 @@ else if [ -z "$JULIA_VERSION" ]; then JULIA_VERSION=1.10 - JULIA_CHANNEL=lts + JULIA_CHANNEL=1.10 else echo "Using environment variable: JULIA_VERSION= $JULIA_VERSION" if [ -z "$JULIA_CHANNEL" ]; then @@ -369,7 +369,7 @@ else activate() { # pyenv activation is necessary on WSL - command -v pyenv &>/dev/null && pyenv local $PYTHON_VERSION + command -v pyenv &>/dev/null && [ -n "`pyenv versions | grep ' $PYTHON_VERSION'`" ] && pyenv local $PYTHON_VERSION poetry env use $PYTHON_VERSION } diff --git a/src/REST/Client.jl b/src/REST/Client.jl index 611608e..93ca3c3 100644 --- a/src/REST/Client.jl +++ b/src/REST/Client.jl @@ -236,9 +236,10 @@ function Taggers.predict(back::LTBackend, file::String; metadata=nothing) connected(tagger) || connect!(tagger) Taggers.push(tagger, file, metadata) Taggers.predict(tagger) - labelfile = Taggers.pull(tagger, dirname(file)) - @assert length(labelfile) == 1 - return labelfile[1] + outputfiles = Taggers.pull(tagger, dirname(file)) + @assert !isempty(outputfiles) + length(outputfiles) == 1 || @warn "Multiple output files" outputfiles + return outputfiles[1] end end diff --git a/src/REST/Model.jl b/src/REST/Model.jl index 9effac9..d712235 100644 --- a/src/REST/Model.jl +++ b/src/REST/Model.jl @@ -1,6 +1,6 @@ module Model -import ..Taggers: Taggers, Tagger +import ..Taggers: Taggers, Tagger, loadmetadata, apply_make_dataset import HTTP: HTTP import JSON3 using OrderedCollections: OrderedDict @@ -187,45 +187,15 @@ function pullfile(lt_backend, backend_dir, model_instance, token, filename) return HTTP.Response(200, header, body) end -function loadmodel(dir, hasinstances=false) - metadata = nothing - for filename in ("metadata", "metadata.json") - if isfile(joinpath(dir, filename)) - metadata = JSON3.read(joinpath(dir, filename)) - break - end - end - name = basename(dir) - T = if hasinstances - Union{AbstractString, Vector{OrderedDict{AbstractString, AbstractString}}} - else - AbstractString - end - model = OrderedDict{AbstractString, T}( - "name" => name, - "description" => "", - "homepage" => "", - ) - if !isnothing(metadata) - for key in keys(model) - key′ = Symbol(key) - if haskey(metadata, key′) - model[key] = metadata[key′] - end - end - end - return model -end - function listtaggers(lt_backend) inventory = Vector{OrderedDict{String, Any}}() backends_dir = lt_backend.root[] for tagging_backend_path in readdir(backends_dir; join=true) Taggers.isbackend(tagging_backend_path) || continue models_dir = joinpath(tagging_backend_path, "models") - models = loadmodel.(readdir(models_dir; join=true)) + models = loadmetadata.(readdir(models_dir; join=true)) isempty(models) && continue - tagging_backend = loadmodel(tagging_backend_path, true) + tagging_backend = loadmetadata(tagging_backend_path, false) tagging_backend["models"] = models push!(inventory, tagging_backend) end @@ -234,14 +204,16 @@ end function predict(lt_backend, backend_dir, model_instance, token) tagger = gettagger(lt_backend, backend_dir, model_instance, token) + make_dataset = apply_make_dataset(tagger, "predict") # blocking; should we run async and expose a token-specific status api call? - Taggers.predict(tagger; skip_make_dataset=true) + Taggers.predict(tagger; make_dataset=make_dataset) end function embed(lt_backend, backend_dir, model_instance, token) tagger = gettagger(lt_backend, backend_dir, model_instance, token) + make_dataset = apply_make_dataset(tagger, "embed") # blocking, like predict - Taggers.embed(tagger; skip_make_dataset=true) + Taggers.embed(tagger; make_dataset=make_dataset) end end diff --git a/src/Taggers.jl b/src/Taggers.jl index e7864cc..6dad6a1 100644 --- a/src/Taggers.jl +++ b/src/Taggers.jl @@ -1,8 +1,11 @@ module Taggers import PlanarLarvae.Formats, PlanarLarvae.Dataloaders +using OrderedCollections: OrderedDict +using JSON3 -export Tagger, isbackend, resetmodel, resetdata, train, predict, finetune, embed +export Tagger, isbackend, resetmodel, resetdata, train, predict, finetune, embed, + loadmetadata, apply_make_dataset struct Tagger backend_dir::String @@ -300,7 +303,9 @@ function run(tagger, switch, kwargs) args = Any[] parsekwargs!(args, kwargs) cmd = tagging_backend_command(tagger) - Base.run(Cmd(`$cmd $switch $args`; dir=tagger.backend_dir)) + cmd = Cmd(`$cmd $switch $args`; dir=tagger.backend_dir) + @info "Running command" cmd + Base.run(cmd) end function train(tagger::Tagger; pretrained_instance=None, kwargs...) @@ -323,4 +328,56 @@ end embed(tagger::Tagger; kwargs...) = run(tagger, "embed", kwargs) +function loadmetadata(dir, instance=true) + metadata = nothing + for filename in ("metadata", "metadata.json") + if isfile(joinpath(dir, filename)) + metadata = JSON3.read(joinpath(dir, filename)) + break + end + end + name = basename(dir) + T = if instance + AbstractString + else + Union{AbstractString, Vector{OrderedDict{AbstractString, AbstractString}}} + end + model = OrderedDict{AbstractString, T}( + "name" => name, + "description" => "", + "homepage" => "", + "make_dataset" => "", + ) + if !isnothing(metadata) + for key in keys(model) + key′ = Symbol(key) + if haskey(metadata, key′) + model[key] = metadata[key′] + end + end + end + return model +end + +function loadmetadata(tagger::Tagger, instance=true) + if instance + loadmetadata(Taggers.modeldir(tagger.backend_dir)) + else + loadmetadata(tagger.backend_dir, true) + end +end + +function apply_make_dataset(tagger::Tagger, step) + # see recipes/patch.sh for a note about the make_dataset entry + @assert step in ("train", "finetune", "predict", "embed") + metadata = loadmetadata(tagger, false) + make_dataset = metadata["make_dataset"] + apply_make_dataset = step in ("train", "finetune") + if !isempty(make_dataset) + apply_make_dataset = make_dataset == "always" || occursin(step, make_dataset) + @debug "apply_make_dataset" metadata apply_make_dataset + end + return apply_make_dataset +end + end # module diff --git a/src/backends.jl b/src/backends.jl index d734ad1..a3ad720 100644 --- a/src/backends.jl +++ b/src/backends.jl @@ -98,8 +98,8 @@ function Taggers.predict(model::Backends, file::String; metadata=nothing) tagger = Tagger(backend_dir, model_instance) # Taggers.push(model, file; metadata=metadata) - # TODO: make the skip_make_dataset option discoverable in the backend - predict(tagger; skip_make_dataset=true) + make_dataset = apply_make_dataset(tagger, "predict") + predict(tagger; make_dataset=make_dataset) labelfile = Taggers.pull(model, dirname(file)) @assert length(labelfile) == 1 return labelfile[1] diff --git a/test/deploy_and_test.sh b/test/deploy_and_test.sh index 942ffd2..b0c0113 100755 --- a/test/deploy_and_test.sh +++ b/test/deploy_and_test.sh @@ -23,7 +23,7 @@ if ! [ -f scripts/install.sh ]; then fi scripts/install.sh --uninstall -scripts/install.sh --with-backend --experimental +scripts/install.sh --with-default-backend ############# ## Maestro ## @@ -74,7 +74,7 @@ if [ -f LarvaTagger_test_data.tgz ]; then else # Not recommended; reproducibility is not guarantee across hosts or architectures yet (cd "$LTROOT" && \ - wget -O- https://dl.pasteur.fr/fop/ppk8GBQf/241127_LarvaTagger_test_data.tgz | tar zxv) + wget -O- https://dl.pasteur.fr/fop/VVIMasjG/241127_LarvaTagger_test_data.tgz | tar zxv) fi if [ "$LOCAL_SCENARII" = "1" ]; then -- GitLab From 51ff20eb2ded73e9713b5e384f0a80d3e1133b93 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=C3=A7ois=20Laurent?= <francois.laurent@posteo.net> Date: Wed, 2 Apr 2025 16:15:32 +0200 Subject: [PATCH 7/8] fix: release-related hotfixes --- README.md | 12 ++++-------- doc/develop.md | 2 ++ recipes/README.md | 6 +----- recipes/release.sh | 26 ++++++++++++++++++++++++++ test/deploy_and_test.sh | 3 ++- test/predict_and_retrain.sh | 2 ++ 6 files changed, 37 insertions(+), 14 deletions(-) create mode 100755 recipes/release.sh diff --git a/README.md b/README.md index 6f7173b..da5807a 100644 --- a/README.md +++ b/README.md @@ -16,6 +16,8 @@ The *LarvaTagger* project is divided into several components. Although this READ This package features a web-based graphical user interface (GUI) for visualizing the tracked larvae and assigning discrete behavior tags, at each time step. +As a web GUI, a public instance can be found at [nyx.pasteur.cloud](https://nyx.pasteur.cloud/larvatagger). Demo data can be found in the [Quick start](#quick-start-with-docker) section below. + A command-line interface (CLI) is also available for batch processing, including the automatic tagging of track data files, training new taggers from labeled data, etc. Although *LarvaTagger.jl* alone comes with no automatic tagger, it is designed to work primarily in combination with [*MaggotUBA*](https://gitlab.pasteur.fr/nyx/MaggotUBA-adapter) for the identification of larval actions or postures. @@ -53,7 +55,7 @@ Change directory (`cd`) to the Downloads directory. In this example, we will ass On macOS and Linux, change the permissions of the script file so that it can be executed: ``` -chmod a+x larvatagger.sh +chmod +x larvatagger.sh ``` The demo data can be opened in the web browser for visual inspection, on macOS and Linux with: @@ -132,12 +134,6 @@ cd LarvaTagger julia --project=. -e 'using Pkg; Pkg.instantiate()' ``` -In May 2024, the gitlab.pasteur.fr server began to request an authentication token on cloning public repositories. -If the `git clone` command requests an authentication token you do not have, do instead: -``` -curl -sSL https://gitlab.pasteur.fr/nyx/larvatagger.jl/-/archive/main/larvatagger.jl-main.tar.gz | tar zxv && mv larvatagger.jl-main LarvaTagger -``` - Calling `Pkg.instantiate` in a copy of the project is preferred over using `Pkg.add`, because *LarvaTagger.jl* depends on several unregistered packages. @@ -218,7 +214,7 @@ Feel free to adjust the value if the 2D view is too small or large. ## Automatic tagging -*LarvaTagger.jl* comes with no automatic tagger per default, unless run using Docker or installed with the *scripts/install.sh* script and the `--with-default-backend` option. +*LarvaTagger.jl* comes with no automatic tagger per default, unless you run the Docker image or you installed LarvaTagger with the *scripts/install.sh* script and the `--with-default-backend` option. To extend the editor with automatic tagging capabilities, see the [recommended installation steps for *TaggingBackends* and *MaggotUBA*](https://gitlab.pasteur.fr/nyx/TaggingBackends#recommended-installation). diff --git a/doc/develop.md b/doc/develop.md index 6648bcc..322d13f 100644 --- a/doc/develop.md +++ b/doc/develop.md @@ -59,3 +59,5 @@ scripts/larvatagger-gui.jl http://localhost:9285 The `docker=docker` environment variable is required if command `podman` is available. The `scripts/larvatagger.sh` script falls back on using `podman` instead of `docker`, if `podman` is available, but it is recommended to perform tests using Docker. In addition, at present, building the image works with Docker buildx only. + +See also the `recipes/release.sh` script. diff --git a/recipes/README.md b/recipes/README.md index 5ad9e8e..f0302b0 100644 --- a/recipes/README.md +++ b/recipes/README.md @@ -149,10 +149,6 @@ Optionally, you can also get the default backend (currently *20230311*) with: ``` scripts/larvatagger.sh build --with-default-backend ``` -Currently, Docker images on Docker Hub are built with: -``` -scripts/larvatagger.sh --target confusion build --with-default-backend -``` If you want another tagger, *e.g.* the *20230129* tagger implemented by the *20230129* branch of the *MaggotUBA-adapter* repository, do: ``` @@ -177,7 +173,7 @@ docker pull flaur/larvatagger ``` Beware that images that ship with a tagging backend are relatively large files (>5GB on disk). -If you are not interested in automatic tagging, use the `flaur/larvatagger:0.19-standalone` image instead. +If you are not interested in automatic tagging, use the `flaur/larvatagger:0.20-standalone` image instead. ### Upgrading diff --git a/recipes/release.sh b/recipes/release.sh new file mode 100755 index 0000000..396d858 --- /dev/null +++ b/recipes/release.sh @@ -0,0 +1,26 @@ +#!/bin/sh + +set -e + +RELEASE=$1 + +if [ -z "$RELEASE" ]; then + echo "Usage: $0 <version-number>" + exit 1 +fi + +docker=docker LARVATAGGER_IMAGE=flaur/larvatagger:$RELEASE-standalone scripts/larvatagger.sh build +docker=docker LARVATAGGER_IMAGE=flaur/larvatagger:$RELEASE-20230311 scripts/larvatagger.sh --target confusion build --with-default-backend +docker tag flaur/larvatagger:$RELEASE-20230311 flaur/larvatagger:latest +docker build -t flaur/larvatagger:$RELEASE-bigfat -f recipes/Dockerfile.pasteurjanelia --no-cache . + +test/predict_and_retrain.sh + +cat <<EOF +Next steps are: +docker login +docker push flaur/larvatagger:$RELEASE-standalone +docker push flaur/larvatagger:$RELEASE-20230311 +docker push flaur/larvatagger:$RELEASE-bigfat +docker push flaur/larvatagger:latest +EOF diff --git a/test/deploy_and_test.sh b/test/deploy_and_test.sh index b0c0113..0de5508 100755 --- a/test/deploy_and_test.sh +++ b/test/deploy_and_test.sh @@ -23,7 +23,8 @@ if ! [ -f scripts/install.sh ]; then fi scripts/install.sh --uninstall -scripts/install.sh --with-default-backend +LARVATAGGER_BRANCH=dev \ + scripts/install.sh --with-default-backend ############# ## Maestro ## diff --git a/test/predict_and_retrain.sh b/test/predict_and_retrain.sh index 771145d..fd68d62 100755 --- a/test/predict_and_retrain.sh +++ b/test/predict_and_retrain.sh @@ -3,6 +3,8 @@ # this script performs a few tests with the Docker image # TODO: implement more use cases as in scenarii.sh +set -e + trap 'rm -rf "$TMPDIR"' EXIT TMPDIR=$(mktemp -d) || exit 1 -- GitLab From bb856490273b414d2819b108621a21d72e60e411 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=C3=A7ois=20Laurent?= <francois.laurent@posteo.net> Date: Wed, 2 Apr 2025 17:16:45 +0200 Subject: [PATCH 8/8] fix: additional controls enabled by default with --server-url --- src/cli_open.jl | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/src/cli_open.jl b/src/cli_open.jl index 73210d8..cdb08e2 100644 --- a/src/cli_open.jl +++ b/src/cli_open.jl @@ -73,6 +73,8 @@ function main(args=ARGS; exit_on_error=false) # kwargs[:viewfactor] = 2 end + proxy_url = parsed_args["--server-url"] + if parsed_args["--viewer"] app = larvaviewer(infile; kwargs...) else @@ -81,12 +83,16 @@ function main(args=ARGS; exit_on_error=false) kwargs[:backend_directory] = backends end kwargs[:manualtag] = string(parsed_args["--manual-label"]) + if !isnothing(proxy_url) + kwargs[:enable_uploads ] = true + kwargs[:enable_new_directories] = true + kwargs[:enable_delete] = true + end app = larvaeditor(infile; kwargs...) end # port = parsed_args["--port"] port = isnothing(port) ? 9284 : parse(Int, port) - proxy_url = parsed_args["--server-url"] if isnothing(proxy_url) proxy_url = "" elseif !startswith(proxy_url, "http") -- GitLab