Merge staging-next into staging

This commit is contained in:
nixpkgs-ci[bot]
2026-08-15 00:11:48 +00:00
committed by GitHub
138 changed files with 4870 additions and 3883 deletions

View File

@@ -466,9 +466,8 @@ nixos/tests/incus/ @adamcstephens
pkgs/by-name/in/incus/ @adamcstephens
pkgs/by-name/lx/lxc* @adamcstephens
# ExpidusOS, Flutter
# Flutter
/pkgs/development/compilers/flutter @RossComputerGuy
/pkgs/desktops/expidus @RossComputerGuy
# GNU Tar & Zip
/pkgs/by-name/gn/gnutar @RossComputerGuy

View File

@@ -1617,6 +1617,13 @@ lib.mapAttrs mkLicense (
fullName = "Universal Permissive License";
};
valveSDK = {
fullName = "Valve Corporation Steamworks SDK Access Agreement";
url = "https://partner.steamgames.com/documentation/sdk_access_agreement";
free = false;
redistributable = true;
};
vim = {
spdxId = "Vim";
fullName = "Vim License";

View File

@@ -7597,12 +7597,6 @@
githubId = 81854406;
name = "Chew Cheng Hong";
};
drew-dirac = {
email = "drew@diracinc.com";
github = "drew-dirac";
githubId = 187309685;
name = "Drew Council";
};
drperceptron = {
github = "drperceptron";
githubId = 92106371;
@@ -17002,6 +16996,17 @@
matrix = "@lux:ontheblueplanet.com";
name = "Lux";
};
luytan = {
email = "luytan@khora.me";
github = "luytan";
githubId = 221864923;
name = "Luytan";
keys = [
{
fingerprint = "E7B7 215C 0DFB 3D8C 17EE 95E0 E0AD 187A 4F2B 41EF";
}
];
};
luz = {
email = "luz666@daum.net";
github = "Luz";

View File

@@ -34,6 +34,8 @@
- [tranquil](https://tangled.org/tranquil.farm/tranquil-pds) is an ATProto PDS (personal data server) implementation in Rust. A featureful, spec conscious and community driven alternative to the Bluesky reference implementation PDS. Available as [services.tranquil-pds](#opt-services.tranquil-pds.enable).
- [Cardwire](https://github.com/OpenGamingCollective/cardwire), a GPU manager for Linux that uses eBPF+LSM hooks to control GPUs. Available as [services.cardwired](#opt-services.cardwired.enable).
- [Moonlight Qt](https://moonlight-stream.org/), a client for playing your PC games on almost any device. Available as [programs.moonlight-qt](#opt-programs.moonlight-qt.enable).
- [RomM](https://romm.app/), a self-hosted ROM manager and player. Available as [services.romm](#opt-services.romm.enable).
@@ -223,6 +225,8 @@
- `boot.supportedFilesystems.ntfs` installs `ntfsprogs-plus` instead of `ntfs3g` on kernel version 7.1 and later, unless `boot.supportedFilesystems.ntfs-3g` is explicitly enabled.
- `services.i2pd` has been refactored to take [RFC42](https://github.com/NixOS/rfcs/blob/master/rfcs/0042-config-option.md)-compliant `settings`. In order to migrate, you will need to move existing config under `settings` and rename them in accordance with the [upstream config format](https://docs.i2pd.website/en/latest/user-guide/configuration/#available-options). In addition, `inTunnels` and `outTunnels` needs to be renamed to `serverTunnels` and `clientTunnels` respectively.
- The `programs.fuse` module, which provides the `fusermount3` executable and the `/etc/fuse.conf` config file, is now opt-in. The obligation to enable it has been shifted to its various consumers (e.g. gvfs, flatpak, appimage, sshfs). This can break fuse consumers at runtime, that don't explicitly declare that dependency with a module, e.g the mounting functionality in various backup tools (borg, restic, rclone, ...).
- `services.plausible` can now again seed an initial admin user declaratively via [`services.plausible.adminUser.email`](#opt-services.plausible.adminUser.email).
@@ -231,6 +235,8 @@
- `services.gitlab.registry` now uses PostgreSQL as database storage for new installations and supports old installations that use the filesystem as metadata storage. It creates the required PostgreSQL database and user. Users can manually migrate their filesystem based metadata storage. See [GitLab Container Registry Migration to database metadata store](#module-services-gitlab-registry-database-migration).
- Enabling [`services.userborn`](#opt-services.userborn.enable) on a system that was previously managed by the default `update-users-groups.pl` script now imports the legacy state from `/var/lib/nixos/` on the first switch. Locked stub entries are added to `/etc/passwd` and `/etc/group` for every name recorded in `uid-map`/`gid-map` that no longer has a live entry, so a previously-used UID/GID cannot be reassigned to a different user. If the import fails, userborn does not start and the user database is left untouched. Inspect `journalctl -u userborn-import-legacy.service`, fix or remove the legacy state, and switch again. The import can be skipped entirely with [`services.userborn.importLegacyState`](#opt-services.userborn.importLegacyState)` = false`.
- The `newuidmap` and `newgidmap` security wrappers are now installed with `cap_setuid`/`cap_setgid` file capabilities instead of the setuid-root bit, matching shadow's `--with-fcaps` install mode and other major distributions. Rootless containers (podman, docker-rootless, unprivileged user namespaces) are unaffected. The only behavioural change is that mapping host uid 0 via `/etc/subuid` (which NixOS never configures by default) additionally requires `cap_setfcap`; users who explicitly grant uid 0 in a subuid range can restore the previous behaviour with `security.wrappers.newuidmap.capabilities = lib.mkForce "cap_setuid,cap_setfcap+ep";`.
- The `authelia` module now uses systemd's `LoadCredential` to load all files defined in `secrets`. As such, these files no longer need to be readable by the authelia user and group: they can for example be set to be only readable by the root user.

View File

@@ -194,7 +194,7 @@ in
redmine = 147;
#seeks = 148; # removed 2020-06-21
prosody = 149;
i2pd = 150;
# i2pd = 150; # dynamically allocated as of 2026-08-07
systemd-coredump = 151;
systemd-network = 152;
systemd-resolve = 153;
@@ -534,7 +534,7 @@ in
redmine = 147;
#seeks = 148; # removed 2020-06-21
prosody = 149;
i2pd = 150;
# i2pd = 150; # dynamically allocated as of 2026-08-07
systemd-network = 152;
systemd-resolve = 153;
systemd-timesync = 154;

View File

@@ -684,6 +684,7 @@
./services/hardware/bolt.nix
./services/hardware/brltty.nix
./services/hardware/buffyboard.nix
./services/hardware/cardwired.nix
./services/hardware/ddccontrol.nix
./services/hardware/deepcool-digital-linux.nix
./services/hardware/dell-bios-fan-control.nix

View File

@@ -0,0 +1,134 @@
{
lib,
config,
pkgs,
...
}:
let
inherit (lib)
mkEnableOption
mkIf
mkOption
types
mkPackageOption
getExe'
;
cfg = config.services.cardwired;
tomlFormat = pkgs.formats.toml { };
in
{
options.services.cardwired = {
enable = mkEnableOption "Cardwire eBPF-based GPU manager daemon";
package = mkPackageOption pkgs "cardwire" { };
settings = mkOption {
type = types.submodule {
options = {
auto_apply_gpu_state = mkOption {
type = types.bool;
default = true;
description = ''
Automatically restore GPU states on manual mode.
'';
};
experimental_nvidia_block = mkOption {
type = types.bool;
default = false;
description = ''
Enable blocking specifics Nvidia files. This setting is experimental
because these files can be shared across multiple Nvidia GPUs.
'';
};
battery_auto_switch = mkOption {
type = types.bool;
default = false;
description = ''
Automatically switch mode on AC power.
'';
};
battery_auto_switch_mode = mkOption {
type = types.enum [
"integrated"
"hybrid"
"manual"
"smart"
];
default = "hybrid";
description = ''
The mode cardwire switches on AC power.
'';
};
external_display_auto_switch = mkOption {
type = types.bool;
default = false;
description = ''
Automatically make GPUs available for displays connected to dGPU-only ports.
'';
};
};
};
default = { };
description = ''
Configuration for {file}`/etc/cardwire.toml`
See <https://opengamingcollective.github.io/cardwire/getting-started/usage>
'';
};
};
config = mkIf cfg.enable {
environment.etc."cardwire/cardwire.toml".source = tomlFormat.generate "cardwire.toml" cfg.settings;
services.dbus.enable = true;
services.dbus.packages = [ cfg.package ];
environment.systemPackages = [ cfg.package ];
systemd.services.cardwired = {
description = "Cardwire Daemon";
restartTriggers = [ config.environment.etc."cardwire/cardwire.toml".source ];
wantedBy = [ "multi-user.target" ];
serviceConfig = {
Type = "dbus";
BusName = "org.opengamingcollective.cardwire";
ExecStart = getExe' cfg.package "cardwired";
Restart = "on-failure";
RestartSec = "5s";
User = "root";
PrivateNetwork = true;
PrivateTmp = true;
ProtectHostname = true;
NoNewPrivileges = true;
ProtectClock = true;
ProtectSystem = "strict";
StateDirectory = "cardwire";
StateDirectoryMode = "0700";
ConfigurationDirectory = "cardwire";
ConfigurationDirectoryMode = "0700";
ProtectHome = "read-only";
ProtectKernelLogs = true;
ProtectControlGroups = true;
ProtectKernelModules = true;
RestrictAddressFamilies = [
"AF_UNIX"
"AF_NETLINK"
];
RestrictNamespaces = true;
RestrictRealtime = true;
RestrictSUIDSGID = true;
LockPersonality = true;
UMask = "0077";
IPAddressDeny = "any";
CapabilityBoundingSet = [
"CAP_SYS_ADMIN"
"CAP_BPF"
"CAP_SYS_PTRACE"
"CAP_DAC_OVERRIDE"
];
};
};
};
}

File diff suppressed because it is too large Load Diff

View File

@@ -96,6 +96,20 @@ in
'';
};
importLegacyState = lib.mkOption {
type = lib.types.bool;
default = !cfg.static;
defaultText = lib.literalExpression "!config.services.userborn.static";
description = ''
Whether to include one-shot migration services that import the state
left behind by the perl activation script (`update-users-groups.pl`),
so id and subid allocations survive the switch to userborn.
Disable this if you want to keep the migration tooling out of your
system closure.
'';
};
};
config = lib.mkIf cfg.enable {
@@ -141,6 +155,33 @@ in
) userCfg.users
);
# One-shot import of update-users-groups.pl state. Runs before
# userborn so removed users' ids are reserved before allocation.
# Remove once the perl path has been gone for two releases.
services.userborn-import-legacy = lib.mkIf cfg.importLegacyState {
wantedBy = [ "sysinit.target" ];
requiredBy = [ "userborn.service" ];
before = [
"userborn.service"
"shutdown.target"
];
after = [ "systemd-remount-fs.service" ];
conflicts = [ "shutdown.target" ];
unitConfig = {
Description = "Import legacy update-users-groups.pl state for userborn";
DefaultDependencies = false;
ConditionPathExists = [
"/var/lib/nixos/uid-map"
"!/var/lib/userborn"
];
};
serviceConfig = {
Type = "oneshot";
RemainAfterExit = true;
ExecStart = "${lib.getExe pkgs.userborn-import-legacy} --nogroup-gid ${toString config.ids.gids.nogroup} ${cfg.passwordFilesLocation}";
};
};
services.userborn = lib.mkIf (!cfg.static) {
wantedBy = [ "sysinit.target" ];
requiredBy = [ "sysinit-reactivation.target" ];

View File

@@ -328,6 +328,7 @@ in
calibre-server = import ./calibre-server.nix { inherit pkgs runTest; };
calibre-web = runTest ./calibre-web.nix;
canaille = runTest ./canaille.nix;
cardwire = runTest ./cardwire.nix;
cassandra = runTest {
imports = [ ./cassandra.nix ];
_module.args.getPackage = pkgs: pkgs.cassandra;
@@ -810,6 +811,7 @@ in
hub = runTest ./git/hub.nix;
hydra = runTest ./hydra;
i18n = runTest ./i18n.nix;
i2pd = runTest ./i2pd.nix;
i3wm = runTest ./i3wm.nix;
icecast = runTest ./icecast.nix;
icingaweb2 = runTest ./icingaweb2.nix;
@@ -1841,6 +1843,7 @@ in
userborn = runTest ./userborn.nix;
userborn-immutable-etc = runTest ./userborn-immutable-etc.nix;
userborn-immutable-users = runTest ./userborn-immutable-users.nix;
userborn-migration = runTest ./userborn-migration.nix;
userborn-mutable-etc = runTest ./userborn-mutable-etc.nix;
userborn-mutable-users = runTest ./userborn-mutable-users.nix;
userborn-static = runTest ./userborn-static.nix;

65
nixos/tests/cardwire.nix Normal file
View File

@@ -0,0 +1,65 @@
{ pkgs, ... }:
{
name = "cardwire";
nodes.machine =
{ pkgs, lib, ... }:
{
services.cardwired.enable = true;
services.dbus.enable = true;
boot.kernelParams = [
"intel_iommu=on"
"iommu=pt"
];
virtualisation.qemu.options = [
"-machine q35,accel=kvm,kernel-irqchip=split"
"-device intel-iommu,intremap=on,device-iotlb=on"
"-vga none"
"-device virtio-gpu-pci,id=igpu,max_outputs=2"
"-device virtio-gpu-pci,id=dgpu,max_outputs=1"
];
};
testScript = ''
machine.start()
machine.wait_for_unit("default.target")
with subtest("Wait for boot and services"):
machine.wait_for_unit("multi-user.target")
machine.wait_for_unit("dbus.service")
machine.wait_for_unit("cardwired.service")
with subtest("Check for DRM Devices"):
dri_out = machine.succeed("ls -a /dev/dri")
assert "renderD128" in dri_out, "Missing DRM"
assert "card0" in dri_out, "Missing DRM"
assert "renderD129" in dri_out, "Missing DRM"
assert "card1" in dri_out, "Missing DRM"
with subtest("Ensure cardwire is started and dbus works"):
machine.wait_until_succeeds("cardwire help")
with subtest("Ensure files are present"):
machine.succeed("cat /etc/cardwire/cardwire.toml")
machine.succeed("cat /var/lib/cardwire/gpu_state.json")
machine.succeed("cat /var/lib/cardwire/mode.json")
with subtest("Switch to Integrated mode"):
assert "renderD128" in machine.succeed("cardwire list"), "Missing RenderD128 in cardwire"
machine.succeed("test -e /dev/dri/renderD129")
assert "Mode has been set to Integrated" in machine.succeed("cardwire set integrated")
machine.fail(": < /dev/dri/renderD129")
assert "integrated" in machine.succeed("cat /var/lib/cardwire/mode.json")
with subtest("Switchback to hybrid mode"):
assert "Mode has been set to Hybrid" in machine.succeed("cardwire set hybrid")
machine.succeed(": < /dev/dri/renderD129")
assert "hybrid" in machine.succeed("cat /var/lib/cardwire/mode.json")
with subtest("Try to block default gpu"):
cardwire_out = machine.fail("cardwire gpu 0 --block 2>&1")
assert "Per GPU block is only available on manual mode" in cardwire_out, "Default gpu got blocked"
'';
}

210
nixos/tests/i2pd.nix Normal file
View File

@@ -0,0 +1,210 @@
{ lib, ... }:
{
name = "i2pd";
meta.maintainers = with lib.maintainers; [ h7x4 ];
nodes = {
server =
{ config, pkgs, ... }:
{
virtualisation.vlans = [ 1 ];
networking = {
useDHCP = false;
interfaces.eth1.useDHCP = false;
firewall.allowedTCPPorts = [ 12345 ];
firewall.allowedUDPPorts = [ 12345 ];
};
systemd.services."test-web-server" = {
wantedBy = [ "multi-user.target" ];
before = [ "i2pd.service" ];
serviceConfig = {
ExecStart = ''
${lib.getExe' pkgs.python3 "python3"} \
-m http.server 8080 \
--bind 127.0.0.1 \
--directory ${pkgs.writeTextDir "index.html" "hello world"}
'';
DynamicUser = true;
};
};
services.i2pd = {
enable = true;
settings = {
# Needed to retrieve b32 address
loglevel = "info";
# Avoid real I2P network ID (2), just in case
# there are any hidden assumptions tied to it.
netid = 77;
host = config.networking.primaryIPAddress;
port = 12345;
# Allow use of local addresses
reservedrange = false;
# No reseed infra available, and we seed netDb manually anyway
reseed.urls = "";
reseed.yggurls = "";
# "router" is the only other node reachable, so every tunnel
# is a single hop through it.
shareddest.inbound.length = 1;
shareddest.outbound.length = 1;
exploratory.inbound.length = 1;
exploratory.outbound.length = 1;
};
serverTunnels.testserver = {
host = "127.0.0.1";
port = 8080;
keys = "testserver-keys.dat";
inbound.length = 1;
outbound.length = 1;
};
};
};
router =
{ config, ... }:
{
virtualisation.vlans = [ 1 ];
networking = {
useDHCP = false;
interfaces.eth1.useDHCP = false;
firewall.allowedTCPPorts = [ 12345 ];
firewall.allowedUDPPorts = [ 12345 ];
};
services.i2pd = {
enable = true;
settings = {
loglevel = "info";
netid = 77;
host = config.networking.primaryIPAddress;
port = 12345;
reservedrange = false;
reseed.urls = "";
reseed.yggurls = "";
floodfill = true;
# "router" has no peer to hop through for its own pools.
shareddest.inbound.length = 0;
shareddest.outbound.length = 0;
exploratory.inbound.length = 0;
exploratory.outbound.length = 0;
};
};
};
client =
{ config, ... }:
{
virtualisation.vlans = [ 1 ];
networking = {
useDHCP = false;
interfaces.eth1.useDHCP = false;
};
# i2pd asserts this exists before it starts, the test script
# overwrites it with the server's actual address once known.
systemd.tmpfiles.rules = [
"f /run/i2pd-secrets/server-destination 0400 root root - unknown.b32.i2p"
];
services.i2pd = {
enable = true;
settings = {
loglevel = "info";
netid = 77;
host = config.networking.primaryIPAddress;
reservedrange = false;
reseed.urls = "";
reseed.yggurls = "";
httpproxy.inbound.length = 1;
httpproxy.outbound.length = 1;
shareddest.inbound.length = 1;
shareddest.outbound.length = 1;
exploratory.inbound.length = 1;
exploratory.outbound.length = 1;
};
clientTunnels.toServer = {
port = 10800;
destination._secret = "/run/i2pd-secrets/server-destination";
inbound.length = 1;
outbound.length = 1;
};
};
};
};
testScript =
# python
''
import re
start_all()
server.wait_for_unit("i2pd.service")
client.wait_for_unit("i2pd.service")
router.wait_for_unit("i2pd.service")
server.wait_for_file("/var/lib/i2pd/router.info")
client.wait_for_file("/var/lib/i2pd/router.info")
router.wait_for_file("/var/lib/i2pd/router.info")
with subtest("Exchange router info"):
server.wait_until_succeeds(
"journalctl -u i2pd -o cat --grep 'Local address \\S+ created'"
)
server_log_line = server.succeed(
"journalctl -u i2pd -o cat --grep 'Local address \\S+ created' --reverse -n 1"
)
server_b32_match = re.search(r"Local address (\S+) created", server_log_line)
assert server_b32_match is not None
server_b32 = server_b32_match.group(1)
client.succeed(
"mkdir -p /run/i2pd-secrets",
f"printf '%s' '{server_b32}.b32.i2p' > /run/i2pd-secrets/server-destination",
)
# We don't have any reseed infra available, so we manually seed each
# of server/client with "router"'s identity, and vice versa.
router.copy_from_machine("/var/lib/i2pd/router.info", "router-identity")
server.copy_from_machine("/var/lib/i2pd/router.info", "server-identity")
client.copy_from_machine("/var/lib/i2pd/router.info", "client-identity")
router_identity = str(router.out_dir / "router-identity" / "router.info")
server.copy_from_host(router_identity, "/var/lib/i2pd/netDb/r0/router.dat")
client.copy_from_host(router_identity, "/var/lib/i2pd/netDb/r0/router.dat")
router.copy_from_host(
str(server.out_dir / "server-identity" / "router.info"),
"/var/lib/i2pd/netDb/r0/server.dat",
)
router.copy_from_host(
str(client.out_dir / "client-identity" / "router.info"),
"/var/lib/i2pd/netDb/r0/client.dat",
)
client.systemctl("restart i2pd.service")
server.systemctl("restart i2pd.service")
router.systemctl("restart i2pd.service")
client.wait_for_unit("i2pd.service")
server.wait_for_unit("i2pd.service")
router.wait_for_unit("i2pd.service")
client.wait_for_open_port(4444)
server.wait_for_unit("test-web-server.service")
with subtest("Request content using the HTTP proxy"):
# This is intended to keep on failing until the client eventually receives
# a LeaseSet from the server.
client.wait_until_succeeds(
f"curl --fail -x 127.0.0.1:4444 http://{server_b32}.b32.i2p/ | grep -q 'hello world'",
)
with subtest("Request content using a port-forwarding tunnel"):
client.wait_until_succeeds(
"curl --fail http://127.0.0.1:10800/ | grep -q 'hello world'",
)
'';
}

View File

@@ -0,0 +1,144 @@
{ lib, ... }:
# Verifies that switching from update-users-groups.pl to userborn honours
# /var/lib/nixos/{uid,gid}-map and declarative-{users,groups}, so removed
# users keep their ids reserved and are not reassigned.
{
name = "userborn-migration";
meta.maintainers = with lib.maintainers; [ rvdp ];
nodes.machine = {
services.userborn.enable = false;
systemd.sysusers.enable = false;
users.mutableUsers = true;
users.users = {
survivor = {
isNormalUser = true;
};
ghost = {
isNormalUser = true;
};
intruder = {
isNormalUser = true;
# Only created under userborn. Must not get ghost's old uid.
enable = lib.mkDefault false;
};
};
specialisation = {
# Still perl-managed. ghost is removed but kept in uid-map.
base-ghost-removed.configuration = {
users.users.ghost.enable = lib.mkForce false;
};
# Switch to userborn with ghost gone and a new unpinned user.
userborn.configuration = {
services.userborn.enable = lib.mkForce true;
users.users.ghost.enable = lib.mkForce false;
users.users.intruder.enable = true;
};
# ghost re-added under userborn. Must keep its original uid.
userborn-revived.configuration = {
services.userborn.enable = lib.mkForce true;
users.users.intruder.enable = true;
};
# The migration service must be removable from the closure.
userborn-without-import.configuration = {
services.userborn.enable = lib.mkForce true;
services.userborn.importLegacyState = false;
users.users.intruder.enable = true;
};
};
};
testScript =
# python
''
import json
machine.wait_for_unit("multi-user.target")
def uid(name: str) -> int:
return int(machine.succeed(f"id --user {name}").strip())
def switch(specialisation: str) -> None:
machine.succeed(
f"/run/booted-system/specialisation/{specialisation}/bin/switch-to-configuration switch 2>&1 | tee /dev/stderr"
)
with subtest("perl: capture allocated state"):
survivor_uid = uid("survivor")
ghost_uid = uid("ghost")
uid_map = json.loads(machine.succeed("cat /var/lib/nixos/uid-map"))
t.assertEqual(uid_map["ghost"], ghost_uid)
t.assertEqual(uid_map["survivor"], survivor_uid)
with subtest("perl: remove ghost"):
switch("base-ghost-removed")
machine.fail("getent passwd ghost")
uid_map = json.loads(machine.succeed("cat /var/lib/nixos/uid-map"))
t.assertEqual(
uid_map["ghost"], ghost_uid, "perl script must retain removed users in uid-map"
)
with subtest("userborn: legacy state is imported"):
# The import only runs while userborn's state directory is absent.
machine.fail("test -e /var/lib/userborn")
switch("userborn")
machine.succeed("test -d /var/lib/userborn")
# ghost must be a locked stub with its original uid.
ghost_passwd = machine.succeed("getent passwd ghost").strip()
t.assertEqual(
int(ghost_passwd.split(":")[2]),
ghost_uid,
f"ghost stub has wrong uid: {ghost_passwd}",
)
ghost_shadow = machine.succeed("getent shadow ghost").strip()
t.assertTrue(
ghost_shadow.split(":")[1].startswith("!"),
f"ghost stub is not locked: {ghost_shadow}",
)
# previous-userborn.json is replaced by ExecStartPost after use,
# so check the journal instead.
machine.succeed(
"journalctl -u userborn-import-legacy.service --grep 'synthesised.*previous-userborn.json'"
)
with subtest("userborn: no uid collision for new user"):
intruder_uid = uid("intruder")
t.assertNotEqual(
intruder_uid,
ghost_uid,
"intruder was allocated ghost's old uid; migration failed to reserve it",
)
t.assertEqual(uid("survivor"), survivor_uid, "survivor uid changed across migration")
with subtest("userborn: revival keeps original uid"):
switch("userborn-revived")
t.assertEqual(
uid("ghost"),
ghost_uid,
"ghost was not revived with its original uid",
)
with subtest("idempotency"):
machine.succeed("systemctl restart userborn-import-legacy.service")
result = machine.succeed(
"systemctl show -p ConditionResult userborn-import-legacy.service"
).strip()
t.assertEqual(result, "ConditionResult=no")
with subtest("legacy import service can be excluded"):
switch("userborn-without-import")
machine.fail("systemctl cat userborn-import-legacy.service")
'';
}

View File

@@ -5086,8 +5086,8 @@ let
mktplcRef = {
name = "vstuc";
publisher = "VisualStudioToolsForUnity";
version = "1.2.2";
hash = "sha256-Yh4nhRTOmQiL34wYnd7Y2OMdl837fexRm5r2hHfhjIg=";
version = "1.3.1";
hash = "sha256-lpkqFXLod/m95DsvIcsb6si0ekIawYO5CI2H6GPML6c=";
};
meta = {
description = "Integrates Visual Studio Code for Unity";

View File

@@ -5,13 +5,13 @@
}:
mkLibretroCore {
core = "mame2003-plus";
version = "0-unstable-2026-07-28";
version = "0-unstable-2026-08-13";
src = fetchFromGitHub {
owner = "libretro";
repo = "mame2003-plus-libretro";
rev = "d6bf36f65f36853120d7e97cdf4fa3720de66728";
hash = "sha256-9fXl/tMtLlKBzpnhFy4Ac5Xp7G2S9kT/qlVMYAChsO8=";
rev = "5bbb84086c548a0ee0738f0b38966d7d4a5ff946";
hash = "sha256-fQ3wIylfkG6Q0LmU/mE3jc/GToubcXPJPSBKpBfThlY=";
};
makefile = "Makefile";

View File

@@ -5,13 +5,13 @@
}:
mkLibretroCore rec {
core = "snes9x2010";
version = "0-unstable-2026-07-23";
version = "0-unstable-2026-08-11";
src = fetchFromGitHub {
owner = "libretro";
repo = "snes9x2010";
rev = "da064275845dfa57e14eb0e5b5c7ddcc117e9f06";
hash = "sha256-uNmgQjIVXMhVinkSZnH6P/Nm4ESPEYjURj5TEf4hoxY=";
rev = "421a8d9449031245f1dfdb632b84548a9f19fddd";
hash = "sha256-/F5/kU8zJzQGhy59c/0CwTM1Pb3aI9+iAWekwf74zDs=";
};
makeFlags = [ "GIT_VERSION=${builtins.substring 0 7 src.rev}" ];

View File

@@ -73,11 +73,11 @@
"vendorHash": "sha256-L9IGENsL8Kibq5O/JOgCxLRUxgS7q9G/NovC/Q7tw48="
},
"auth0_auth0": {
"hash": "sha256-jODs72Ve7OZ/lzhcZVZpjDvpl5m0pPvRVhz+35M2Afs=",
"hash": "sha256-lqlQglt3zbNkoE4ORBWIq85r7/SYucIOPgIzJ7NrYaQ=",
"homepage": "https://registry.terraform.io/providers/auth0/auth0",
"owner": "auth0",
"repo": "terraform-provider-auth0",
"rev": "v1.54.0",
"rev": "v1.54.1",
"spdx": "MPL-2.0",
"vendorHash": "sha256-gQHnTp3reX/1fmwQqjpqtjlb2z3wYk8E8vRf73jh48E="
},
@@ -472,22 +472,22 @@
"vendorHash": "sha256-xl92EeXmhKNEbdCmzfd0p8EVkCjLi2gM47A69IXXAyE="
},
"goharbor_harbor": {
"hash": "sha256-+HtvOLOD8PEYky+ws/deCcX8Tea5pR/77eb7LXJhseg=",
"hash": "sha256-daV5W/fLW4+5XG0Lh8rcF7A9CKHq232/9kiMT5OzI1s=",
"homepage": "https://registry.terraform.io/providers/goharbor/harbor",
"owner": "goharbor",
"repo": "terraform-provider-harbor",
"rev": "v3.12.3",
"rev": "v3.12.4",
"spdx": "MIT",
"vendorHash": "sha256-Zie1NyDPnk+UX2UBxGlpJaok9PeRyu0/tuMQS7WCvZI="
"vendorHash": "sha256-vEQ++yk7BYUsgejppHiRJeMGzG4QOLfdPixCTLz9sbI="
},
"grafana_grafana": {
"hash": "sha256-PtMpesJeG7HEJQ7AaRCu2UrkX6yVpxKZeyieoaoGjlg=",
"hash": "sha256-pd7bq2m8PC/kWWoWd04MpIrrQPYKRVRGFTbXJjTGuac=",
"homepage": "https://registry.terraform.io/providers/grafana/grafana",
"owner": "grafana",
"repo": "terraform-provider-grafana",
"rev": "v4.43.0",
"rev": "v4.45.1",
"spdx": "MPL-2.0",
"vendorHash": "sha256-Lq0DV5RJRqi1oZNm4XRoJbDE71uGBjR8KjTghucpf7M="
"vendorHash": "sha256-B/XiioxXXK3dzlKTDH8y7QQMx0ztqQ7TaE1Cbt8Kj3M="
},
"gridscale_gridscale": {
"hash": "sha256-FAKvQ/MEod5Ck0PG4ffQ+gQp6zZ0JDRXPOrOiDpWMls=",
@@ -1481,13 +1481,13 @@
"vendorHash": "sha256-GRnVhGpVgFI83Lg34Zv1xgV5Kp8ioKTFV5uaqS80ATg="
},
"vpsfreecz_vpsadmin": {
"hash": "sha256-Yi5mFhJsGGPg3IyOdgV2mTfj5ZVd76vu3/JFNrh5+Wc=",
"hash": "sha256-T+az9OH9/ZMSJewZpC9VLSXOZ5N/wz00VRnl9Ab4aeI=",
"homepage": "https://registry.terraform.io/providers/vpsfreecz/vpsadmin",
"owner": "vpsfreecz",
"repo": "terraform-provider-vpsadmin",
"rev": "v1.2.0",
"rev": "v1.3.0",
"spdx": "MPL-2.0",
"vendorHash": "sha256-rUYHapEVqRupLOPVbcAH8YP0cuXclMmYTQUkqeOwCN0="
"vendorHash": "sha256-98lrEH7j4Fl0oSEoL75e0h+8ySLacPK2k0OehY3jqhA="
},
"vultr_vultr": {
"hash": "sha256-hK4/Pzj0UtWDLQS3cRMC73ZRr20HCWqI+jUlTUHcHaw=",

View File

@@ -0,0 +1,38 @@
{
lib,
fetchFromGitHub,
nix-update-script,
rustPlatform,
versionCheckHook,
}:
rustPlatform.buildRustPackage (finalAttrs: {
pname = "acdi";
version = "0.5.2";
__structuredAttrs = true;
src = fetchFromGitHub {
owner = "vral-parmar";
repo = "acdi";
tag = "v${finalAttrs.version}";
hash = "sha256-IYFsUi+MF6fjzSS+2Muoh08lD6tCMxz9wjubX7Inlbk=";
};
cargoHash = "sha256-J9raJea/7jjVdYn/8WvjkPDXzOs5jzPyyAWEsqr2BhM=";
nativeInstallCheckInputs = [ versionCheckHook ];
doInstallCheck = true;
passthru.updateScript = nix-update-script { };
meta = {
description = "Automated Cryptography Discovery & Inventory Scanner";
homepage = "https://github.com/vral-parmar/acdi";
changelog = "https://github.com/vral-parmar/acdi/blob/${finalAttrs.src.rev}/CHANGELOG.md";
license = lib.licenses.mit;
maintainers = with lib.maintainers; [ fab ];
mainProgram = "acdi";
};
})

View File

@@ -2,6 +2,7 @@
appimageTools,
fetchurl,
lib,
python3,
}:
let
@@ -24,7 +25,12 @@ appimageTools.wrapType2 {
substituteInPlace $out/share/applications/arduino-ide.desktop --replace-fail 'Exec=AppRun --no-sandbox %U' 'Exec=arduino-ide %U'
'';
extraPkgs = pkgs: [ pkgs.libsecret ];
extraPkgs = pkgs: [
pkgs.libsecret
(python3.withPackages (ps: [
ps.pyserial # for esptool
]))
];
meta = {
description = "Open-source electronics prototyping platform";

View File

@@ -7,13 +7,13 @@
buildGoModule (finalAttrs: {
pname = "bit-logo";
version = "0.3.0";
version = "0.4.0";
src = fetchFromGitHub {
owner = "paulilaaso";
repo = "bit";
tag = "v${finalAttrs.version}";
hash = "sha256-iLwWKn8csoRkr5H8R2kpZVZCxsL0LDWHNvNoxyM6y98=";
hash = "sha256-CCRJFxVHe7FNGX5XC2SYWAzcMVNlHjUBt0El41Zo9Ww=";
};
vendorHash = "sha256-Zxw0NyZfM42ytn+vDExLwRgNLWsdGVLC3iNVpQd8VMw=";

View File

@@ -0,0 +1,128 @@
{
lib,
stdenv,
rustPlatform,
fetchFromGitHub,
hwdata,
libdrm,
bpf-linker,
pkg-config,
nixosTests,
makeBinaryWrapper,
udev,
wayland,
libxkbcommon,
vulkan-loader,
libGL,
installShellFiles,
libxcb,
libglvnd,
versionCheckHook,
}:
rustPlatform.buildRustPackage (finalAttrs: {
pname = "cardwire";
version = "0.12.0";
__structuredAttrs = true;
src = fetchFromGitHub {
owner = "opengamingcollective";
repo = "cardwire";
tag = "v${finalAttrs.version}";
hash = "sha256-WuXFztiy6G2HYCu3KpKrjR8YCpcLePfGEZ+f71x1WnM=";
};
cargoHash = "sha256-8eJSxL9RkHtbUxXuKPvyxhvSJD/0JeNaEM/oZf0n2Q4=";
postPatch = ''
# Workaround to build cardwire-ebpf, when RUSTC_BOOTSTRAP is set to 1
# aya-build appends build_std to the cargo args, removing this
# make the crate builds
# <https://github.com/aya-rs/aya/blob/15a0de1b363e51d55d0fca4245df54a61e8d5521/aya-build/src/lib.rs#L151-L172>
substituteInPlace ../cardwire-*-vendor/*/aya-build-*/src/lib.rs \
--replace-fail "if use_build_std" "if !use_build_std"
substituteInPlace crates/cardwire-daemon/src/core/pci/pci_device.rs \
--replace-fail "/usr/share/hwdata/pci.ids" "${hwdata}/share/hwdata/pci.ids"
substituteInPlace crates/cardwire-daemon/src/core/gpu/device_info.rs \
--replace-fail "/usr/share/libdrm/amdgpu.ids" "${libdrm}/share/libdrm/amdgpu.ids"
'';
env = {
RUSTFLAGS = "-C target-feature=";
RUSTC_BOOTSTRAP = 1;
};
nativeBuildInputs = [
pkg-config
bpf-linker
makeBinaryWrapper
installShellFiles
];
buildInputs = [
libxcb
udev
];
postInstall = ''
install -Dm444 ./assets/org.opengamingcollective.cardwire.conf \
$out/share/dbus-1/system.d/org.opengamingcollective.cardwire.conf
install -Dm444 ./assets/org.opengamingcollective.cardwire.metainfo.xml \
$out/share/metainfo/org.opengamingcollective.cardwire.metainfo.xml
install -Dm444 ./assets/cardwire-gui.desktop \
$out/share/applications/cardwire-gui.desktop
for icon in ./assets/icons/*.svg; do
install -Dm444 "$icon" "$out/share/icons/hicolor/scalable/apps/$(basename "$icon")"
done
wrapProgram $out/bin/cardwired \
--prefix LD_LIBRARY_PATH : ${
lib.makeLibraryPath [
vulkan-loader
libglvnd
]
}
wrapProgram $out/bin/cardwire-gui \
--prefix LD_LIBRARY_PATH : ${
lib.makeLibraryPath [
wayland
libxkbcommon
vulkan-loader
libGL
]
}
''
+ lib.optionalString (stdenv.buildPlatform.canExecute stdenv.hostPlatform) ''
installShellCompletion --cmd cardwire \
--fish <($out/bin/cardwire completion fish) \
--bash <($out/bin/cardwire completion bash) \
--zsh <($out/bin/cardwire completion zsh)
'';
doInstallCheck = true;
nativeInstallCheckInputs = [ versionCheckHook ];
passthru.tests.cardwire = nixosTests.cardwire;
meta = {
description = "GPU manager for laptop and workstation";
platforms = [
"x86_64-linux"
"aarch64-linux"
];
homepage = "https://opengamingcollective.github.io/cardwire/";
changelog = "https://github.com/OpenGamingCollective/cardwire/releases/tag/${finalAttrs.src.tag}";
license = lib.licenses.gpl3Only;
maintainers = with lib.maintainers; [
luytan
];
mainProgram = "cardwire";
};
})

View File

@@ -0,0 +1,38 @@
{
lib,
rustPlatform,
fetchFromGitHub,
nix-update-script,
versionCheckHook,
}:
rustPlatform.buildRustPackage (finalAttrs: {
pname = "cbom";
version = "0.1.1";
__structuredAttrs = true;
src = fetchFromGitHub {
owner = "qelens";
repo = "cbom";
tag = "v${finalAttrs.version}";
hash = "sha256-xwMuipbwgzhaORPQ9U0eVi+68Ml7J/SH+naWcjV5n2w=";
};
cargoHash = "sha256-+vvABoPyaeH6+CPITeT7OtsLfVfdZQfjF8DU1yE1Hmw=";
nativeInstallCheckInputs = [ versionCheckHook ];
doInstallCheck = true;
passthru.updateScript = nix-update-script { };
meta = {
description = "CBOM Generator & PQC Readiness Scanner";
homepage = "https://github.com/qelens/cbom";
changelog = "https://github.com/qelens/cbom/releases/tag/${finalAttrs.src.tag}";
license = lib.licenses.mpl20;
maintainers = with lib.maintainers; [ fab ];
mainProgram = "cbom";
};
})

View File

@@ -54,7 +54,6 @@ stdenv.mkDerivation (finalAttrs: {
platforms = lib.platforms.all;
maintainers = with lib.maintainers; [
raskin
drew-dirac
ylannl
];
};

View File

@@ -17,16 +17,16 @@
}:
stdenv.mkDerivation (finalAttrs: {
pname = "dashy-ui";
version = "4.5.6";
version = "4.5.10";
src = fetchFromGitHub {
owner = "lissy93";
repo = "dashy";
tag = finalAttrs.version;
hash = "sha256-gj1U9w4GkY/CZ9tyXmONIQOUIYZAK0NhgKDek7zjRm4=";
hash = "sha256-oHTe2vilrtvApLQ7x8L+upTgkhz2TsXsbA8KcvsZg64=";
};
yarnOfflineCache = fetchYarnDeps {
yarnLock = finalAttrs.src + "/yarn.lock";
hash = "sha256-UjcA3z3jnnDizjYIb1D76OWC7n9UcN0HhQnwfW7y8BU=";
hash = "sha256-43z3gn58eb7Dh9QXLDoeAJAViCQX+8IeSN4xx+hYfPI=";
};
passthru = {

View File

@@ -13,7 +13,7 @@
SDL_audiolib,
simpleini,
flac,
fmt,
fmt_11,
libogg,
libpng,
libtiff,
@@ -90,7 +90,7 @@ stdenv.mkDerivation (finalAttrs: {
buildInputs = [
bzip2
flac
fmt
fmt_11
libogg
libpng
libtiff

View File

@@ -3,6 +3,10 @@
rustPlatform,
fetchFromGitHub,
versionCheckHook,
# full SMART attribute tables. Else, fallback to basic verified/failing flag from diskutil
withSmartmontools ? false,
smartmontools,
}:
rustPlatform.buildRustPackage (finalAttrs: {
@@ -22,16 +26,19 @@ rustPlatform.buildRustPackage (finalAttrs: {
nativeCheckInputs = [ versionCheckHook ];
doInstallCheck = true;
buildInputs = lib.optionals withSmartmontools [ smartmontools ];
versionCheckProgramArg = [ "-V" ];
doInstallCheck = true;
meta = {
description = "Single-host, read-only disk diagnostics TUI";
homepage = "https://github.com/matthart1983/diskwatch";
homepage = "https://www.netwatchlabs.com/labs/diskwatch";
changelog = "https://github.com/matthart1983/diskwatch/releases/tag/${finalAttrs.src.tag}";
license = lib.licenses.mit;
maintainers = with lib.maintainers; [ fab ];
maintainers = with lib.maintainers; [
fab
tomasrivera
];
mainProgram = "diskwatch";
};
})

View File

@@ -24,18 +24,18 @@
stdenv.mkDerivation (finalAttrs: {
pname = "flare";
version = "0.22.0";
version = "0.22.1";
src = fetchFromGitLab {
owner = "schmiddi-on-mobile";
repo = "flare";
tag = finalAttrs.version;
hash = "sha256-amFFQIR5BFJLsNarhw4Ov2Jo+zFZJt+vtavNup75QgI=";
hash = "sha256-ddBNRCPS0ykgigUzhufDfwlv6+97zdCYwQxlm7zLt/E=";
};
cargoDeps = rustPlatform.fetchCargoVendor {
inherit (finalAttrs) pname version src;
hash = "sha256-tssFy/dMh0UGBrBsLoibuMuDXOqIVQ9/FgOHz4IVU5o=";
hash = "sha256-Sb9n7QIEPkdj5I+LP5WZRCezr/y86Oe6VZh+hhyiafk=";
};
nativeBuildInputs = [

View File

@@ -7,16 +7,16 @@
buildGoModule (finalAttrs: {
pname = "git-wt";
version = "0.29.0";
version = "0.29.1";
src = fetchFromGitHub {
owner = "k1LoW";
repo = "git-wt";
tag = "v${finalAttrs.version}";
hash = "sha256-1u0GDC1Sc4Xy4URuM6TnR/ENsdIWa94Ixu3mL6WrmFg=";
hash = "sha256-8WePARXoLC9NV8Z5PSkM2A4UXFxAZOhT6QbSCY+jtaw=";
};
vendorHash = "sha256-ppbY3ZJo2L/FbWlOiywqk6W4kVDQKkwf5VjRHucb78A=";
vendorHash = "sha256-P8+KiaGZt8j4rRQ4OKP/pQOU8+g2H1snra5dS9Dd8tc=";
nativeCheckInputs = [ git ];

View File

@@ -4,35 +4,37 @@
fetchurl,
cmake,
coreutils,
python,
root,
enablePython ? false,
python ? null,
}:
assert enablePython -> python != null;
let
pythonVersion = with lib.versions; "${major python.version}${minor python.version}";
withPython = python != null;
# ensure that root is built with the same python interpreter, as it links against numpy
root_py = if withPython then root.override { python3 = python; } else root;
root_py = if enablePython then root.override { python3 = python; } else root;
in
stdenv.mkDerivation rec {
stdenv.mkDerivation (finalAttrs: {
pname = "hepmc3";
version = "3.3.1";
src = fetchurl {
url = "https://hepmc.web.cern.ch/hepmc/releases/HepMC3-${version}.tar.gz";
sha256 = "sha256-CCQBYLDyjcMpOqTWHOZeLWfNWXrPb6ykOfLkZiX355M=";
url = "https://hepmc.web.cern.ch/hepmc/releases/HepMC3-${finalAttrs.version}.tar.gz";
hash = "sha256-CCQBYLDyjcMpOqTWHOZeLWfNWXrPb6ykOfLkZiX355M=";
};
nativeBuildInputs = [
cmake
]
++ lib.optional withPython python.pkgs.pythonImportsCheckHook;
++ lib.optional enablePython python.pkgs.pythonImportsCheckHook;
buildInputs = [
root_py
]
++ lib.optional withPython python;
++ lib.optional enablePython python;
# error: invalid version number in 'MACOSX_DEPLOYMENT_TARGET=11.0'
preConfigure =
@@ -44,9 +46,9 @@ stdenv.mkDerivation rec {
cmakeFlags = [
"-DHEPMC3_CXX_STANDARD=17"
"-DHEPMC3_ENABLE_PYTHON=${if withPython then "ON" else "OFF"}"
"-DHEPMC3_ENABLE_PYTHON=${if enablePython then "ON" else "OFF"}"
]
++ lib.optionals withPython [
++ lib.optionals enablePython [
"-DHEPMC3_PYTHON_VERSIONS=${if python.isPy3k then "3.X" else "2.X"}"
"-DHEPMC3_Python_SITEARCH${pythonVersion}=${placeholder "out"}/${python.sitePackages}"
];
@@ -67,4 +69,4 @@ stdenv.mkDerivation rec {
platforms = lib.platforms.unix;
maintainers = with lib.maintainers; [ veprbl ];
};
}
})

View File

@@ -10,13 +10,13 @@
gcc16Stdenv.mkDerivation (finalAttrs: {
pname = "hyprutils";
version = "0.14.0";
version = "0.14.1";
src = fetchFromGitHub {
owner = "hyprwm";
repo = "hyprutils";
tag = "v${finalAttrs.version}";
hash = "sha256-XnAVV+H4f8Xdv0yZcSwJ5kCjLyE8fHxPeLX6a3HSrAU=";
hash = "sha256-WGAG9f7YnEjAu33WWxL6kkOyZGgcpiASwdNxpkwr2AQ=";
};
nativeBuildInputs = [

View File

@@ -17,25 +17,27 @@
glib,
gtk4,
libadwaita,
libcdio,
openssl,
pango,
wimlib,
nix-update-script,
}:
stdenv.mkDerivation (finalAttrs: {
pname = "impression";
version = "3.7.0";
version = "3.8.0";
src = fetchFromGitLab {
owner = "adhami3310";
repo = "Impression";
tag = "v${finalAttrs.version}";
hash = "sha256-EyVbK+E9X9q+O/2RItJDXjQNsLZ3cn2YmK9Ct98w8IQ=";
hash = "sha256-kUes+hNtoi6jvZFDon2pFUPsLq7wOJ2SDrPBGzg3AIo=";
};
cargoDeps = rustPlatform.fetchCargoVendor {
inherit (finalAttrs) pname version src;
hash = "sha256-Mvpy5aDeu4qycSj+fp4DfRNLv6T2Ksqgjt5GFTkjS6U=";
hash = "sha256-PL+PJ5Diy9WvAuBJQQNp8bvjPK3Uvd0Um/B6lZHypXw=";
};
nativeBuildInputs = [
@@ -57,8 +59,10 @@ stdenv.mkDerivation (finalAttrs: {
glib
gtk4
libadwaita
libcdio
openssl
pango
wimlib
];
passthru = {

View File

@@ -18,13 +18,13 @@
}:
stdenv.mkDerivation (finalAttrs: {
pname = "karakeep";
version = "0.33.0";
version = "0.33.1";
src = fetchFromGitHub {
owner = "karakeep-app";
repo = "karakeep";
tag = "cli/v${finalAttrs.version}";
hash = "sha256-WL4M2rpbIDUTUUCuw2T5tG4VCMGZaLsWq+BCAQBa2Sc=";
hash = "sha256-/rEVeNxLgqeoxJTyzArZAGzAbJjfOjHuG+zpOnf40Mk=";
};
patches = [
@@ -60,7 +60,7 @@ stdenv.mkDerivation (finalAttrs: {
;
pnpm = pnpm_11;
fetcherVersion = 4;
hash = "sha256-JhD1soZj8l6ZVtTOSZc1lMfWfi3R0PU/SsVHEvr50PI=";
hash = "sha256-0ExBj87CbzgTis9/Z0J2d82051SXlEOgwXO+jAWxCi4=";
};
buildPhase = ''
runHook preBuild

View File

@@ -2,8 +2,9 @@
lib,
stdenv,
buildFHSEnv,
symlinkJoin,
makeWrapper,
testers,
writeShellScript,
kiro-cli-unwrapped,
# On Wayland, kiro-cli shells out to wl-clipboard (wl-copy/wl-paste) for
# clipboard access. Enabling this puts wl-clipboard on the runtime PATH so
@@ -15,45 +16,52 @@
let
inherit (kiro-cli-unwrapped) version meta;
# Each of kiro-cli's user-facing commands, run inside a minimal FHS sandbox.
# All of kiro-cli's user-facing commands run inside one minimal FHS sandbox.
# The sandbox provides a standard /lib64/ld-linux-x86-64.so.2 plus libgcc_s/
# libstdc++ (via stdenv.cc.cc.lib), so the generic-glibc `bun` that
# kiro-cli-chat extracts at runtime just works — no binary patching of the
# extracted asset, and no build-time execution of the tool.
fhsFor =
executableName:
buildFHSEnv {
pname = executableName;
inherit version;
inherit executableName;
runScript = executableName;
#
# buildFHSEnv provides a single entry point per environment, so instead of
# building one environment per command (which would give kiro-cli, kiro-cli-chat
# and kiro-cli-term separate derivations, each with its own unfree license and
# each requiring its own entry in the unfree allowlist), we build a single
# environment whose entry point dispatches to whichever command is passed to
# it, and expose one thin wrapper per command via `extraInstallCommands`.
# This keeps the unfree allowlist to two entries (`kiro-cli` and
# `kiro-cli-unwrapped`) instead of four. The three binaries ship in the same
# upstream artifact and share the same runtime needs, so there is no
# per-command sandbox to lose.
fhsenv = buildFHSEnv {
pname = "kiro-cli";
inherit version;
targetPkgs =
pkgs:
[
kiro-cli-unwrapped
pkgs.stdenv.cc.cc.lib # libstdc++.so.6, libgcc_s.so.1 for the extracted bun
]
++ lib.optional waylandSupport pkgs.wl-clipboard;
runScript = writeShellScript "kiro-cli" ''
command="$1"
shift
exec "$command" "$@"
'';
targetPkgs =
pkgs:
[
kiro-cli-unwrapped
pkgs.stdenv.cc.cc.lib # libstdc++.so.6, libgcc_s.so.1 for the extracted bun
]
++ lib.optional waylandSupport pkgs.wl-clipboard;
nativeBuildInputs = [ makeWrapper ];
extraInstallCommands = ''
mkdir -p $out/libexec/kiro-cli
mv $out/bin/kiro-cli $out/libexec/kiro-cli/kiro-cli-wrapper
for command in kiro-cli kiro-cli-chat kiro-cli-term; do
makeWrapper "$out/libexec/kiro-cli/kiro-cli-wrapper" "$out/bin/$command" \
--add-flags "$command"
done
'';
meta = meta // {
mainProgram = executableName;
};
};
in
# Darwin ships a normal .app bundle with no embedded-bun problem, so it needs
# no FHS sandbox; hand back the unwrapped derivation under the public name.
if stdenv.hostPlatform.isLinux then
symlinkJoin {
name = "kiro-cli-${version}";
# Preserve the strictDeps = true that the unwrapped derivation exposes, so
# the top-level attribute keeps it too (nixpkgs-vet NPV-165).
strictDeps = true;
paths = map fhsFor [
"kiro-cli"
"kiro-cli-chat"
"kiro-cli-term"
];
passthru = {
unwrapped = kiro-cli-unwrapped;
tests.version = testers.testVersion {
@@ -64,7 +72,15 @@ if stdenv.hostPlatform.isLinux then
inherit version;
};
};
inherit meta;
}
meta = meta // {
mainProgram = "kiro-cli";
};
};
in
# Darwin ships a normal .app bundle with no embedded-bun problem, so it needs
# no FHS sandbox; hand back the unwrapped derivation under the public name.
if stdenv.hostPlatform.isLinux then
fhsenv
else
kiro-cli-unwrapped.overrideAttrs { pname = "kiro-cli"; }

View File

@@ -38,13 +38,13 @@ assert enableTools -> enableAudio && enableEmulation && enableLibplayer;
stdenv.mkDerivation (finalAttrs: {
pname = "libvgm";
version = "0-unstable-2026-06-23";
version = "0-unstable-2026-08-11";
src = fetchFromGitHub {
owner = "ValleyBell";
repo = "libvgm";
rev = "867223e7c33d63de115d1ab955f784c44f19040a";
hash = "sha256-GuvngfkqLy3E5Esb+HOnY6G1XYDyDzv1yz+NccaclGI=";
rev = "61fc6725644886abc3168e240e4e51588d74bdf7";
hash = "sha256-b/jd0ltSICRarZW/2RJYgNM/qyMaweOJFEZ2KHDCpnE=";
};
outputs = [

View File

@@ -0,0 +1,89 @@
{
lib,
stdenv,
fetchFromGitHub,
cmake,
libGL,
libx11,
libxt,
imath,
openimageio,
python3Packages,
pythonSupport ? false,
testers,
}:
stdenv.mkDerivation (finalAttrs: {
pname = "materialx";
version = "1.39.5";
src = fetchFromGitHub {
owner = "AcademySoftwareFoundation";
repo = "MaterialX";
rev = "v${finalAttrs.version}";
hash = "sha256-7aY1SI5b5hVjvTtucQh6XpkwkhPZWDhsTVYLKM667/k=";
};
strictDeps = true;
nativeBuildInputs = [
cmake
]
++ lib.optional pythonSupport python3Packages.python
++ lib.optional (
pythonSupport && stdenv.buildPlatform == stdenv.hostPlatform
) python3Packages.pythonImportsCheckHook;
buildInputs = [
imath
openimageio
libGL
];
# create meta package providing dist-info for python3Packages.materialx
propagatedBuildInputs =
lib.optionals (!stdenv.hostPlatform.isDarwin) [
libx11
libxt
]
++ lib.optionals pythonSupport [
(python3Packages.mkPythonMetaPackage {
inherit (finalAttrs) pname version meta;
})
];
cmakeFlags = [
(lib.cmakeBool "MATERIALX_BUILD_OIIO" true)
(lib.cmakeBool "MATERIALX_BUILD_SHARED_LIBS" (!stdenv.hostPlatform.isStatic))
(lib.cmakeBool "MATERIALX_BUILD_PYTHON" pythonSupport)
(lib.cmakeBool "MATERIALX_BUILD_GEN_MSL" true)
];
pythonImportsCheck = [ "MaterialX" ];
postInstall = lib.optionalString pythonSupport ''
# Make python lib properly accessible
target_dir=$out/${python3Packages.python.sitePackages}
mkdir -p $(dirname $target_dir)
# required for cmake to find the bindings, when included in other projects
ln -s $out/python $target_dir
'';
passthru = {
tests = {
cmake-config = testers.hasCmakeConfigModules {
moduleNames = [ "MaterialX" ];
package = finalAttrs.finalPackage;
};
};
};
meta = {
changelog = "https://github.com/AcademySoftwareFoundation/MaterialX/blob/v${finalAttrs.version}/CHANGELOG.md";
description = "Open standard for representing rich material and look-development content in computer graphics";
homepage = "https://materialx.org";
maintainers = with lib.maintainers; [ gador ];
platforms = lib.platforms.unix;
license = lib.licenses.asl20;
};
})

View File

@@ -74,14 +74,14 @@ let
in
rustPlatform.buildRustPackage (finalAttrs: {
pname = "mistral-rs";
version = "0.9.0";
version = "0.9.1";
__structuredAttrs = true;
src = fetchFromGitHub {
owner = "EricLBuehler";
repo = "mistral.rs";
tag = "v${finalAttrs.version}";
hash = "sha256-3p/e7UZ8BLwT+dpb61NmzX2Z1QxxEgkgjlNzv5lWybM=";
hash = "sha256-5W/CBFw28xBC7GnbpQ9jxRAdxXBtTdsD3X/YNR6z6iI=";
};
patches = [
@@ -130,7 +130,7 @@ rustPlatform.buildRustPackage (finalAttrs: {
""
'';
cargoHash = "sha256-TULJ3mEAWp1ktPDPeBbUJGHhsEuo5T2qh3/JpS+8+ds=";
cargoHash = "sha256-VivnZNtIjnu1JOKaE7nEIse8300oB9oqGP0aly+9/OQ=";
nativeBuildInputs = [
pkg-config
@@ -242,6 +242,8 @@ rustPlatform.buildRustPackage (finalAttrs: {
# mistralrs: error while loading shared libraries: libcuda.so.1: cannot open shared object file: No such file or directory
doInstallCheck = !cudaSupport;
__darwinAllowLocalNetworking = true;
passthru = {
tests = {
withMkl = lib.optionalAttrs (hostPlatform.isLinux && hostPlatform.isx86_64) (

View File

@@ -35,8 +35,8 @@ rustPlatform.buildRustPackage (finalAttrs: {
meta = {
description = "Real-time network diagnostics in your terminal.";
homepage = "https://github.com/matthart1983/netwatch";
changelog = "https://github.com/matthart1983/netwatch/releases/tag/${finalAttrs.src.tag}";
homepage = "https://www.netwatchlabs.com/labs/netwatch";
changelog = "https://github.com/matthart1983/netwatch/blob/${finalAttrs.src.tag}/CHANGELOG.md";
license = lib.licenses.mit;
mainProgram = "netwatch";
maintainers = with lib.maintainers; [ tomasrivera ];

View File

@@ -8,16 +8,16 @@
rustPlatform.buildRustPackage (finalAttrs: {
pname = "nxv";
version = "0.7.1";
version = "0.7.3";
src = fetchFromGitHub {
owner = "utensils";
repo = "nxv";
tag = "v${finalAttrs.version}";
hash = "sha256-CkwOJaOumxBx5kGOfkEHDmEBxrTzGXVNKJdZld3uxdA=";
hash = "sha256-PJs+qvzLKBa3b5a4ZWGU02BVAqyoZj3+mhphBTSmpS0=";
};
cargoHash = "sha256-itYpea4CBSGVdzFiRtA1Yib3U2mFyMmo/P9jicrJCrc=";
cargoHash = "sha256-2nZpwkaVedkH3dHkaB/QSTthylwMw6S08JhgiZaBX7M=";
# Tests use mockito which needs to bind to localhost
__darwinAllowLocalNetworking = true;

View File

@@ -7,16 +7,16 @@
buildGoModule (finalAttrs: {
pname = "payload-dumper-go";
version = "1.3.0";
version = "2.0.0";
src = fetchFromGitHub {
owner = "ssut";
repo = "payload-dumper-go";
tag = finalAttrs.version;
hash = "sha256-TFnBWylOoyleuBx3yYfHl1kWO6jVBiqsi8AMYLMuuk0=";
hash = "sha256-A9WVPn/MeLTt1ySmN8Xge/Ye8BDhtETJstxB6mI5FFU=";
};
vendorHash = "sha256-XeD47PsFjDT9777SNE8f2LbKZ1cnL5HNPr3Eg7UIpJ0=";
vendorHash = "sha256-hjVgIVOwci1IXaV+0AHgB36pMSgQsYi3A+9NIMsSz54=";
buildInputs = [ xz ];

View File

@@ -66,7 +66,10 @@ stdenv.mkDerivation (finalAttrs: {
homepage = "https://github.com/raspberrypi/pico-sdk";
changelog = "https://github.com/raspberrypi/pico-sdk/releases/tag/${finalAttrs.version}";
license = lib.licenses.bsd3;
maintainers = with lib.maintainers; [ muscaln ];
maintainers = with lib.maintainers; [
muscaln
nulleric
];
platforms = lib.platforms.unix;
};
})

View File

@@ -62,7 +62,10 @@ stdenv.mkDerivation (finalAttrs: {
changelog = "https://github.com/raspberrypi/picotool/releases/tag/${finalAttrs.version}";
mainProgram = "picotool";
license = lib.licenses.bsd3;
maintainers = with lib.maintainers; [ muscaln ];
maintainers = with lib.maintainers; [
muscaln
nulleric
];
platforms = lib.platforms.unix;
};
})

View File

@@ -36,7 +36,10 @@ stdenv.mkDerivation (finalAttrs: {
homepage = "https://github.com/raspberrypi/pico-sdk";
changelog = "https://github.com/raspberrypi/pico-sdk/releases/tag/${finalAttrs.version}";
license = lib.licenses.bsd3;
maintainers = with lib.maintainers; [ emilytrau ];
maintainers = with lib.maintainers; [
emilytrau
nulleric
];
platforms = lib.platforms.unix;
mainProgram = "pioasm";
};

View File

@@ -11,14 +11,15 @@
kdePackages,
lib,
libGL,
libdecor,
libjack2,
libpulseaudio,
libusb1,
libx11,
libxcursor,
libxext,
libxrandr,
libxxf86vm,
libjack2,
libpulseaudio,
libusb1,
openal,
pciutils,
pipewire,
@@ -105,6 +106,7 @@ symlinkJoin {
libxrandr
libxxf86vm
wayland
libdecor
udev # oshi

View File

@@ -11,16 +11,16 @@
rustPlatform.buildRustPackage (finalAttrs: {
pname = "proto";
version = "0.60.0";
version = "0.60.2";
src = fetchFromGitHub {
owner = "moonrepo";
repo = "proto";
rev = "v${finalAttrs.version}";
hash = "sha256-Fzrio8LwfZW//k10aqj/gwVDcrmui/GlQS/BmZASG1A=";
hash = "sha256-Lp5H5dpjb1M31uIRv1EaicXnWEIDAYsiQj36ANaQsm0=";
};
cargoHash = "sha256-QoX2ubtcjhTM7Q5pTPdI2QH1ZC9rssG3KHdocdQ26Lk=";
cargoHash = "sha256-kxAtZXhKbU6Apgn1S2byjK19Ig2RdBv+dOpb33YoC3A=";
buildInputs = lib.optionals stdenv.hostPlatform.isDarwin [
libiconv

View File

@@ -5,16 +5,16 @@
}:
buildGoModule rec {
pname = "protolint";
version = "0.56.4";
version = "0.57.0";
src = fetchFromGitHub {
owner = "yoheimuta";
repo = "protolint";
rev = "v${version}";
hash = "sha256-2R+TW8z3XgjavK19PGy9hMpN8WOSeWbb/vcSWbbBmJc=";
hash = "sha256-n3/O1ZgEDrPfPaytT88dfZeECd65rIPs7SBb9uwJXEU=";
};
vendorHash = "sha256-RS0t7n6pLYVKHluQtXsMjYL1SvN7IZFdKmkxOI8wFoE=";
vendorHash = "sha256-XuURqNSOJXb3kg8tyohixS12I2M+UWbYhhyhHOJvNo4=";
# Something about the way we run tests causes issues. It doesn't happen
# when using "go test" directly:

View File

@@ -0,0 +1 @@
{ python3Packages }: with python3Packages; toPythonApplication pyldapsearch

View File

@@ -5,21 +5,25 @@
boost,
fastjet,
fixDarwinDylibNames,
hepmc,
hepmc2,
lhapdf,
rsync,
zlib,
}:
stdenv.mkDerivation rec {
let
hepmc = hepmc2;
in
stdenv.mkDerivation (finalAttrs: {
pname = "pythia";
version = "8.317";
src = fetchurl {
url = "https://pythia.org/download/pythia83/pythia${
builtins.replaceStrings [ "." ] [ "" ] version
builtins.replaceStrings [ "." ] [ "" ] finalAttrs.version
}.tgz";
sha256 = "sha256-GuVR0U2sSV3f5rNEeSA16+QQ/mxgBNRKM14Ozg50Wt8=";
hash = "sha256-GuVR0U2sSV3f5rNEeSA16+QQ/mxgBNRKM14Ozg50Wt8=";
};
nativeBuildInputs = [ rsync ] ++ lib.optionals stdenv.hostPlatform.isDarwin [ fixDarwinDylibNames ];
@@ -56,4 +60,4 @@ stdenv.mkDerivation rec {
platforms = lib.platforms.unix;
maintainers = with lib.maintainers; [ veprbl ];
};
}
})

View File

@@ -33,27 +33,21 @@
exiv2,
libraw,
libjxl,
fmt,
}:
stdenv.mkDerivation (finalAttrs: {
pname = "rawtherapee";
version = "5.12";
version = "5.13";
src = fetchurl {
# The developers ask not to use the tarball from GitHub releases, see
# https://www.rawtherapee.com/downloads/5.12/#news-relevant-to-package-maintainers
url = "https://rawtherapee.com/shared/source/rawtherapee-${finalAttrs.version}.tar.xz";
hash = "sha256-2abBBTfWSihbxGVnX+WaqpTOMiOCPfvs8K4slZkILVc=";
url = "https://github.com/RawTherapee/RawTherapee/releases/download/${finalAttrs.version}/rawtherapee-${finalAttrs.version}.tar.xz";
hash = "sha256-I73/SxgX4SdMEalLEdIcrFnpwbHSCXldMZRxDuc+d78=";
};
postPatch = ''
# https://github.com/NixOS/nixpkgs/issues/475835
# https://github.com/RawTherapee/RawTherapee/issues/7443#issuecomment-3014132156
# remove for 5.13
substituteInPlace rtengine/procparams.cc --replace \
'outputProfile(options.rtSettings.srgb),' \
'outputProfile("RTv4_sRGB"),'
cat <<EOF > ReleaseInfo.cmake
set(GIT_DESCRIBE ${finalAttrs.version})
set(GIT_BRANCH ${finalAttrs.version})
@@ -102,6 +96,7 @@ stdenv.mkDerivation (finalAttrs: {
exiv2
libraw
libjxl
fmt
]
++ lib.optionals stdenv.hostPlatform.isLinux [
libcanberra-gtk3
@@ -114,6 +109,7 @@ stdenv.mkDerivation (finalAttrs: {
"-DPROC_TARGET_NUMBER=2"
"-DCACHE_NAME_SUFFIX=\"\""
"-DWITH_SYSTEM_LIBRAW=\"ON\""
"-DWITH_SYSTEM_FMT=\"ON\""
"-DWITH_JXL=\"ON\""
]
++ lib.optionals stdenv.hostPlatform.isDarwin [
@@ -145,6 +141,9 @@ stdenv.mkDerivation (finalAttrs: {
description = "RAW converter and digital photo processing software";
homepage = "http://www.rawtherapee.com/";
license = lib.licenses.gpl3Plus;
sourceProvenance = with lib.sourceTypes; [
fromSource
];
maintainers = with lib.maintainers; [
jcumming
mahe

View File

@@ -11,19 +11,16 @@
buildGoModule (finalAttrs: {
pname = "resticprofile";
version = "0.31.0";
version = "0.33.1";
src = fetchFromGitHub {
owner = "creativeprojects";
repo = "resticprofile";
tag = "v${finalAttrs.version}";
hash = "sha256-ezelvyroQG1EW3SU63OVHJ/T4qjN5DRllvPIXnei1Z4=";
hash = "sha256-L6L1JfBa/nsrwtvIw2U++jIDLJTxxweqcXQ3SomtS1A=";
};
postPatch = ''
substituteInPlace schedule_jobs.go \
--replace-fail "os.Executable()" "\"$out/bin/resticprofile\", nil"
substituteInPlace shell/command.go \
--replace-fail '"bash"' '"${lib.getExe bash}"'
@@ -32,7 +29,7 @@ buildGoModule (finalAttrs: {
'';
vendorHash = "sha256-M9S6F/Csz7HnOq8PSWjpENKm1704kVx9zDts1ieraTE=";
vendorHash = "sha256-dYzx27HtIME/mrtQrRg7064Ii20715FVYj5uw4Aian0=";
ldflags = [
"-X main.version=${finalAttrs.version}"
@@ -57,6 +54,15 @@ buildGoModule (finalAttrs: {
rm util/tempdir_test.go # expects normal environment
'';
checkFlags =
let
skippedTests = [
# mount: fusermount: exec: "fusermount": executable file not found in $PATH
"TestMemFS"
];
in
[ "-skip=^${builtins.concatStringsSep "$|^" skippedTests}$" ];
installPhase = ''
runHook preInstall
@@ -85,7 +91,10 @@ buildGoModule (finalAttrs: {
lgpl3 # bash shell completion
];
mainProgram = "resticprofile";
maintainers = with lib.maintainers; [ tomasajt ];
platforms = lib.platforms.linux ++ lib.platforms.darwin;
maintainers = with lib.maintainers; [
tomasajt
bbigras
];
platforms = lib.platforms.unix;
};
})

View File

@@ -184,12 +184,7 @@ stdenv.mkDerivation (finalAttrs: {
license = with lib.licenses; [
gpl3Only
# For libsteam_api.so
(
unfreeRedistributable
// {
url = "https://partner.steamgames.com/documentation/sdk_access_agreement";
}
)
valveSDK
];
maintainers = with lib.maintainers; [ weirdrock ];
mainProgram = "rimsort";

View File

@@ -68,17 +68,7 @@ rustPlatform.buildRustPackage (finalAttrs: {
changelog = "https://github.com/jsnli/Samira/releases/tag/v${finalAttrs.version}";
license = [
lib.licenses.gpl3
(
# while the license itself is unfree, it allows redistributing files
# inside "redistributable_bin/" directory, that `libsteam_api.so`
# conveniently is inside that folder
lib.licenses.unfreeRedistributableFirmware
// {
fullName = "Valve Corporation Steamworks SDK Access Agreement";
shortName = "valveSDKLicense";
url = "https://partner.steamgames.com/documentation/sdk_access_agreement";
}
)
lib.licenses.valveSDK
];
# the libsteam_api.so supports only x86_64-linux
platforms = [ "x86_64-linux" ];

View File

@@ -5,8 +5,9 @@
fetchFromGitHub,
pkg-config,
stdenv,
libogg,
flac,
fmt,
fmt_11,
}:
stdenv.mkDerivation (finalAttrs: {
@@ -29,8 +30,9 @@ stdenv.mkDerivation (finalAttrs: {
buildInputs = [
SDL2
libogg # required by flac
flac
fmt
fmt_11
];
strictDeps = true;

View File

@@ -9,14 +9,14 @@
}:
rustPlatform.buildRustPackage (finalAttrs: {
pname = "sea-orm-cli";
version = "2.0.1";
version = "2.0.2";
src = fetchCrate {
inherit (finalAttrs) pname version;
hash = "sha256-TpHNjY8r9a8d6senzeQLJl/n0hytytx+NV+atjyti1k=";
hash = "sha256-tkyZSsTE1a08AIif5NNkBazASs+pvBgP69CnZhEZkhw=";
};
cargoHash = "sha256-eE777DE1g87NobNPHdMhqCFc8RZtQyL/QM29iFJV8p4=";
cargoHash = "sha256-4+rFHOBRyUGF6DXxT4Y54Y2s4F9MGcNF/ELWj/4fPWo=";
strictDeps = true;
__structuredAttrs = true;

View File

@@ -10,13 +10,13 @@
}:
stdenvNoCC.mkDerivation (finalAttrs: {
pname = "sketchybar-app-font";
version = "2.0.71";
version = "2.0.75";
src = fetchFromGitHub {
owner = "kvndrsslr";
repo = "sketchybar-app-font";
tag = "v${finalAttrs.version}";
hash = "sha256-Xyj2yPU7Sd6WTWHrVAmx2JGGvUihM5jq79yXbLUz9Qk=";
hash = "sha256-o6Nq1vQWv2YMd0S2jUPtxPK3KrKyS1bF3RBNEM5ZHBg=";
};
pnpmDeps = fetchPnpmDeps {

View File

@@ -11,7 +11,7 @@
}:
stdenv.mkDerivation (finalAttrs: {
pname = "speakeasy-cli";
version = "1.791.3";
version = "1.793.1";
sourceRoot = ".";
src =
@@ -33,15 +33,15 @@ stdenv.mkDerivation (finalAttrs: {
sources = {
"x86_64-linux" = fetchurl {
url = "https://github.com/speakeasy-api/speakeasy/releases/download/v${finalAttrs.version}/speakeasy_linux_amd64.zip";
hash = "sha256-NMkvraMA2vz1PQkvTL8OBwi9KiyapCt432sS4KFkMA4=";
hash = "sha256-2gsFSOKf+r2vRk6m6Rv6Ox2Bp8U1MDdWihAQe05Y5Ss=";
};
"aarch64-darwin" = fetchurl {
url = "https://github.com/speakeasy-api/speakeasy/releases/download/v${finalAttrs.version}/speakeasy_darwin_arm64.zip";
hash = "sha256-KJ24NQRnidoCFZaswL1u3ep0UUCK5P8G60IDQJ1nmUI=";
hash = "sha256-laJqK432x4N3CkrVNVELOxroDxypLLBy1aOj2ja2LcI=";
};
"aarch64-linux" = fetchurl {
url = "https://github.com/speakeasy-api/speakeasy/releases/download/v${finalAttrs.version}/speakeasy_linux_arm64.zip";
hash = "sha256-JU7u4+vFzxiQRico3ulDCZlpF14I3JEbrd1csNkuY9M=";
hash = "sha256-XosrVGX38WhF+KbBKMU/Q6CYPsqx1mt/abTE16/P1Zo=";
};
};
updateScript = writeShellScript "update-speakeasy" ''

View File

@@ -24,14 +24,15 @@ rustPlatform.buildRustPackage (finalAttrs: {
doInstallCheck = true;
versionCheckProgramArg = [ "-V" ];
meta = {
description = "Single-host system diagnostics TUI tool";
homepage = "https://github.com/matthart1983/syswatch";
homepage = "https://www.netwatchlabs.com/labs/syswatch";
changelog = "https://github.com/matthart1983/syswatch/releases/tag/${finalAttrs.src.tag}";
license = lib.licenses.mit;
maintainers = with lib.maintainers; [ fab ];
maintainers = with lib.maintainers; [
fab
tomasrivera
];
mainProgram = "syswatch";
};
})

View File

@@ -8,17 +8,24 @@
stdenv.mkDerivation (finalAttrs: {
pname = "ta-lib";
version = "0.7.1";
__structuredAttrs = true;
strictDeps = true;
src = fetchFromGitHub {
owner = "TA-Lib";
repo = "ta-lib";
tag = "v${finalAttrs.version}";
hash = "sha256-tme5YuTWdf4lCsWXF97kSeka7Vmqte0vTjwtaUNN+kA=";
};
nativeBuildInputs = [ autoreconfHook ];
meta = {
description = "Add technical analysis to your own financial market trading applications";
mainProgram = "ta-lib-config";
homepage = "https://ta-lib.org/";
changelog = "https://github.com/TA-Lib/ta-lib-python/blob/${finalAttrs.src.rev}/CHANGELOG";
license = lib.licenses.bsd3;
platforms = lib.platforms.linux;
maintainers = with lib.maintainers; [ rafael ];

View File

@@ -19,16 +19,16 @@ let
in
buildNpmPackage rec {
pname = "teams-for-linux";
version = "2.14.1";
version = "2.15.0";
src = fetchFromGitHub {
owner = "IsmaelMartinez";
repo = "teams-for-linux";
tag = "v${version}";
hash = "sha256-0urL/M7XBBPB+RiLglUx0CQUii+Fji1dXurha/2URug=";
hash = "sha256-PYRl0Q7vsx7nKz7pkoCg3f3rRIcgCAvGiALQxHEOIjE=";
};
npmDepsHash = "sha256-F8FxTkVDfCLp0ukNm9/ixWtglYRiJt9+va6qJdB06qI=";
npmDepsHash = "sha256-FPnkCO1zf5Ts2arOa0InC7l4esRs4AuXYlVF/OYR6AI=";
nativeBuildInputs = [
makeWrapper

View File

@@ -0,0 +1,112 @@
# This file is automatically @generated by Cargo.
# It is not intended for manual editing.
version = 4
[[package]]
name = "anyhow"
version = "1.0.104"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "330a5ed07fa54e4702c9d6c4174f74427fc0ef6e214bbd677ae50a5099946470"
[[package]]
name = "itoa"
version = "1.0.18"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8f42a60cbdf9a97f5d2305f08a87dc4e09308d1276d28c869c684d7777685682"
[[package]]
name = "memchr"
version = "2.8.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "cf8baf1c55e62ffcace7a9f06f4bd9cd3f0c4beb022d3b367256b91b87513d98"
[[package]]
name = "proc-macro2"
version = "1.0.107"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "985e7ec9bb745e6ce6535b544d84d6cd6f7ad8bd711c398938ae983b91a766d9"
dependencies = [
"unicode-ident",
]
[[package]]
name = "quote"
version = "1.0.47"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1fbf4db142a473a8d80c26bbf18454ed458bf8d26c8219c331daecfdbd079001"
dependencies = [
"proc-macro2",
]
[[package]]
name = "serde"
version = "1.0.229"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4148590afebada386688f18773da617792bf2ef03ffc1e4cbd2b1d45b023e0ba"
dependencies = [
"serde_core",
]
[[package]]
name = "serde_core"
version = "1.0.229"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "67dca2c9c51e58a4791a4b1ed58308b39c64224d349a935ab5039aa360942a48"
dependencies = [
"serde_derive",
]
[[package]]
name = "serde_derive"
version = "1.0.229"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e7a5d71263a5a7d47b41f6b3f06ba276f10cc18b0931f1799f710578e2309348"
dependencies = [
"proc-macro2",
"quote",
"syn",
]
[[package]]
name = "serde_json"
version = "1.0.151"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c841b55ecdae098c80dcae9cf767f6f8a0c2cdb3416bbef72181df4d0fe73f14"
dependencies = [
"itoa",
"memchr",
"serde",
"serde_core",
"zmij",
]
[[package]]
name = "syn"
version = "3.0.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a207d6d6a2b7fc470b80443726053f18a2481b7e1eee970597051596567987a3"
dependencies = [
"proc-macro2",
"quote",
"unicode-ident",
]
[[package]]
name = "unicode-ident"
version = "1.0.24"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e6e4313cd5fcd3dad5cafa179702e2b244f760991f45397d14d4ebf38247da75"
[[package]]
name = "userborn-import-legacy"
version = "0.1.0"
dependencies = [
"anyhow",
"serde_json",
]
[[package]]
name = "zmij"
version = "1.0.23"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "29666d0abbfad1e3dc4dcf6144730dd3a3ab225bbbdac83319345b1b44ccfc1b"

View File

@@ -0,0 +1,14 @@
[package]
name = "userborn-import-legacy"
description = "One-shot migration from update-users-groups.pl state to userborn"
version = "0.1.0"
edition = "2024"
license = "MIT"
[dependencies]
anyhow = "1"
serde_json = "1"
[profile.release]
lto = true
strip = true

View File

@@ -0,0 +1,38 @@
{
lib,
rustPlatform,
nixosTests,
}:
rustPlatform.buildRustPackage {
__structuredAttrs = true;
strictDeps = true;
pname = "userborn-import-legacy";
version = (lib.importTOML ./Cargo.toml).package.version;
src = builtins.filterSource (name: _: !(lib.hasSuffix ".nix" name)) ./.;
cargoLock.lockFile = ./Cargo.lock;
passthru.tests = { inherit (nixosTests) userborn-migration; };
meta = {
description = "One-shot migration from update-users-groups.pl state to userborn";
longDescription = ''
Runs once before userborn on systems migrating from
update-users-groups.pl. Adds locked stub entries to
/etc/{passwd,group,shadow} for every name in
/var/lib/nixos/{uid,gid}-map without a live entry so freed ids are
not reassigned, and creates previous-userborn.json based on
declarative-{users,groups}.
Temporary. Will be removed once the perl implementation has been
gone for two NixOS releases.
'';
license = lib.licenses.mit;
maintainers = with lib.maintainers; [ rvdp ];
platforms = lib.platforms.linux;
mainProgram = "userborn-import-legacy";
};
}

View File

@@ -0,0 +1,397 @@
//! One-shot migration from `update-users-groups.pl` state in `/var/lib/nixos`
//! to the on-disk databases userborn treats as authoritative.
//!
//! userborn never deletes passwd/group entries, so /etc/passwd is its
//! uid-map. We make it a superset of /var/lib/nixos/uid-map by adding a
//! locked stub for every recorded name without a live entry, so the id is
//! neither reassigned nor lost if the name is later re-added.
//!
//! Runs once: the unit is skipped when `/var/lib/userborn` already exists,
//! which userborn creates on its first run. Will be removed once the perl
//! implementation is gone.
use std::collections::{BTreeMap, HashMap, HashSet};
use std::fs::{self, File, OpenOptions};
use std::io::{self, Write};
use std::os::unix::fs::{DirBuilderExt, OpenOptionsExt, PermissionsExt};
use std::path::{Path, PathBuf};
use std::process::ExitCode;
use anyhow::{Context, Result, bail};
const LEGACY: &str = "/var/lib/nixos";
const USERBORN_STATE: &str = "/var/lib/userborn";
const PREVIOUS_NAME: &str = "previous-userborn.json";
fn main() -> ExitCode {
match run() {
Ok(()) => ExitCode::SUCCESS,
Err(e) => {
// printk prefix for journald level.
eprintln!("<3>userborn-import-legacy: {e:#}");
ExitCode::FAILURE
}
}
}
#[derive(Debug)]
struct Args {
directory: PathBuf,
/// Primary group for stub passwd entries when the legacy gid-map has no
/// record for the user's name. Passed in from `config.ids.gids.nogroup`;
/// the stub is locked and has no shell, so any valid gid would do.
nogroup_gid: u32,
}
impl Args {
const USAGE: &str = "usage: userborn-import-legacy [--nogroup-gid GID] [DIRECTORY]";
fn parse() -> Result<Self> {
let mut directory: Option<PathBuf> = None;
let mut nogroup_gid = 65534u32;
let mut iter = std::env::args().skip(1);
while let Some(arg) = iter.next() {
match arg.as_str() {
"--nogroup-gid" => {
nogroup_gid = iter
.next()
.context("--nogroup-gid requires a value")?
.parse()
.context("--nogroup-gid must be an integer")?;
}
"--help" | "-h" => {
println!("{}", Self::USAGE);
std::process::exit(0);
}
opt if opt.starts_with('-') => {
bail!("unknown option {opt:?}\n{}", Self::USAGE);
}
_ if directory.is_some() => {
bail!("unexpected extra argument {arg:?}\n{}", Self::USAGE);
}
_ => directory = Some(PathBuf::from(arg)),
}
}
Ok(Self {
directory: directory.unwrap_or_else(|| PathBuf::from("/etc")),
nogroup_gid,
})
}
}
fn run() -> Result<()> {
let args = Args::parse()?;
create_dir_recursive(&args.directory, 0o755)?;
import_ids(&args)?;
// Creating userborn's state directory marks the import as done. Only
// create it after a successful import so failed runs are retried on
// the next boot.
create_dir_recursive(Path::new(USERBORN_STATE), 0o755)?;
synthesise_previous_config()?;
Ok(())
}
fn info(msg: &str) {
eprintln!("<6>userborn-import-legacy: {msg}");
}
fn warn(msg: &str) {
eprintln!("<4>userborn-import-legacy: {msg}");
}
/// Load `/var/lib/nixos/{uid,gid}-map`: `{"name": id, ...}`.
fn load_id_map(path: &Path) -> Result<BTreeMap<String, u32>> {
match fs::read(path) {
Ok(bytes) => {
serde_json::from_slice(&bytes).with_context(|| format!("parsing {}", path.display()))
}
Err(e) if e.kind() == io::ErrorKind::NotFound => Ok(BTreeMap::new()),
Err(e) => Err(e).with_context(|| format!("reading {}", path.display())),
}
}
/// Return `(names, id->name)` from a passwd/group style file.
fn load_colon_db(path: &Path) -> Result<(HashSet<String>, HashMap<u32, String>)> {
let mut names = HashSet::new();
let mut by_id = HashMap::new();
let text = match fs::read_to_string(path) {
Ok(t) => t,
Err(e) if e.kind() == io::ErrorKind::NotFound => return Ok((names, by_id)),
Err(e) => return Err(e).with_context(|| format!("reading {}", path.display())),
};
for line in text.lines() {
let mut fields = line.splitn(4, ':');
let Some(name) = fields.next().filter(|n| !n.is_empty()) else {
// Tolerate blank lines, warn on anything else.
if !line.is_empty() {
warn(&format!(
"{}: ignoring line without a name: {line:?}",
path.display()
));
}
continue;
};
let _passwd = fields.next();
let Some(id) = fields.next().and_then(|s| s.parse::<u32>().ok()) else {
warn(&format!(
"{}: ignoring entry {name:?} without a numeric id",
path.display()
));
continue;
};
names.insert(name.to_owned());
by_id.insert(id, name.to_owned());
}
Ok((names, by_id))
}
/// Create `path` and any missing parents with the given mode.
///
/// Doesn't touch the permissions of directories that already exist.
fn create_dir_recursive(path: &Path, mode: u32) -> Result<()> {
fs::DirBuilder::new()
.recursive(true)
.mode(mode)
.create(path)
.with_context(|| format!("creating {}", path.display()))
}
/// Atomically replace `path` with `content`: write a temporary file in the
/// same directory, fsync it, and rename it into place, so a crash cannot
/// leave a partially written database behind for the next boot.
fn atomic_write(path: &Path, content: &[u8], mode: u32) -> Result<()> {
let dir = path.parent().context("path has no parent")?;
let tmp = path.with_added_extension("tmp");
let mut f = OpenOptions::new()
.write(true)
.create(true)
.truncate(true)
.mode(mode)
.open(&tmp)
.with_context(|| format!("creating {}", tmp.display()))?;
// The mode passed to open is masked by the umask, so make sure we set
// the actual permissions.
f.set_permissions(fs::Permissions::from_mode(mode))
.with_context(|| format!("chmod {}", tmp.display()))?;
f.write_all(content)
.with_context(|| format!("writing {}", tmp.display()))?;
f.sync_all()?;
drop(f);
fs::rename(&tmp, path)
.with_context(|| format!("renaming {} to {}", tmp.display(), path.display()))?;
File::open(dir)?.sync_all()?;
Ok(())
}
/// Append `lines` to `path` via a whole-file rewrite and an atomic rename,
/// inserting a newline first if the file lacks a trailing one. Assumes the
/// file already exists (see `touch`).
fn append_lines(path: &Path, lines: &[String]) -> Result<()> {
if lines.is_empty() {
return Ok(());
}
let mut content = fs::read(path).with_context(|| format!("reading {}", path.display()))?;
if !content.is_empty() && !content.ends_with(b"\n") {
content.push(b'\n');
}
for line in lines {
content.extend_from_slice(line.as_bytes());
content.push(b'\n');
}
// mode() returns the full st_mode; mask off the file type bits.
let mode = fs::metadata(path)
.with_context(|| format!("stat {}", path.display()))?
.permissions()
.mode()
& 0o7777;
atomic_write(path, &content, mode)
}
fn touch(path: &Path, mode: u32) -> Result<()> {
if path.exists() {
return Ok(());
}
File::create(path).with_context(|| format!("creating {}", path.display()))?;
fs::set_permissions(path, fs::Permissions::from_mode(mode))
.with_context(|| format!("chmod {}", path.display()))?;
Ok(())
}
fn import_ids(args: &Args) -> Result<()> {
let passwd = args.directory.join("passwd");
let group = args.directory.join("group");
let shadow = args.directory.join("shadow");
touch(&passwd, 0o644)?;
touch(&group, 0o644)?;
touch(&shadow, 0o000)?;
let (mut user_names, mut user_ids) = load_colon_db(&passwd)?;
let (mut group_names, mut group_ids) = load_colon_db(&group)?;
let legacy = Path::new(LEGACY);
let gid_map = load_id_map(&legacy.join("gid-map"))?;
let uid_map = load_id_map(&legacy.join("uid-map"))?;
let mut new_group = Vec::new();
for (name, &gid) in &gid_map {
if group_names.contains(name) {
continue;
}
if let Some(owner) = group_ids.get(&gid) {
warn(&format!(
"gid {gid} from gid-map for {name:?} is already used by {owner:?}; skipping"
));
continue;
}
info(&format!("reserving gid {gid} for removed group {name:?}"));
new_group.push(format!("{name}:x:{gid}:"));
group_names.insert(name.clone());
group_ids.insert(gid, name.clone());
}
append_lines(&group, &new_group)?;
let mut new_passwd = Vec::new();
let mut new_shadow = Vec::new();
for (name, &uid) in &uid_map {
if user_names.contains(name) {
continue;
}
if let Some(owner) = user_ids.get(&uid) {
warn(&format!(
"uid {uid} from uid-map for {name:?} is already used by {owner:?}; skipping"
));
continue;
}
let gid = gid_map.get(name).copied().unwrap_or(args.nogroup_gid);
info(&format!("reserving uid {uid} for removed user {name:?}"));
new_passwd.push(format!(
"{name}:x:{uid}:{gid}::/var/empty:/run/current-system/sw/bin/nologin"
));
new_shadow.push(format!("{name}:!*:1::::::"));
user_names.insert(name.clone());
user_ids.insert(uid, name.clone());
}
append_lines(&passwd, &new_passwd)?;
append_lines(&shadow, &new_shadow)?;
Ok(())
}
/// Populate `previous-userborn.json` from `declarative-{users,groups}`.
///
/// Under `mutableUsers`, userborn diffs the current config against the
/// previous one to decide which entries to lock/drain vs leave alone.
/// Without a previous config on the first run, formerly-declarative users
/// dropped in the same switch would be treated as imperative and left
/// enabled. Translate the perl script's declarative-{users,groups} into
/// the minimal JSON userborn expects so its first run behaves correctly.
fn synthesise_previous_config() -> Result<()> {
let previous = Path::new(USERBORN_STATE).join(PREVIOUS_NAME);
if previous.exists() {
// Unreachable via the unit's ConditionPathExists, but never clobber
// a real previous config.
warn(&format!(
"{} already exists; not overwriting",
previous.display()
));
return Ok(());
}
let names = |path: &Path| -> Result<Vec<serde_json::Value>> {
let text = match fs::read_to_string(path) {
Ok(t) => t,
Err(e) if e.kind() == io::ErrorKind::NotFound => return Ok(Vec::new()),
Err(e) => return Err(e).with_context(|| format!("reading {}", path.display())),
};
Ok(text
.split_whitespace()
.map(|n| serde_json::json!({ "name": n }))
.collect())
};
let legacy = Path::new(LEGACY);
let doc = serde_json::json!({
"users": names(&legacy.join("declarative-users"))?,
"groups": names(&legacy.join("declarative-groups"))?,
});
atomic_write(&previous, &serde_json::to_vec(&doc)?, 0o644)
.with_context(|| format!("writing {}", previous.display()))?;
info(&format!(
"synthesised {} from declarative-users/groups",
previous.display()
));
Ok(())
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn colon_db() {
let dir = tempdir();
let p = dir.join("passwd");
fs::write(
&p,
"root:x:0:0::/root:/bin/sh\n\
nobody:x:65534:65534::/var/empty:/bin/nologin\n\
:::\n\
bogus:x:notanumber:0::\n",
)
.unwrap();
let (names, ids) = load_colon_db(&p).unwrap();
assert!(names.contains("root"));
assert!(names.contains("nobody"));
assert_eq!(ids.get(&0), Some(&"root".to_owned()));
assert!(!names.contains("bogus"));
}
#[test]
fn append_adds_missing_newline() {
let dir = tempdir();
let p = dir.join("f");
fs::write(&p, "a:x:1:").unwrap();
append_lines(&p, &["b:x:2:".into()]).unwrap();
assert_eq!(fs::read_to_string(&p).unwrap(), "a:x:1:\nb:x:2:\n");
}
#[test]
fn append_keeps_mode() {
let dir = tempdir();
let p = dir.join("shadow");
fs::write(&p, "a:!:1::::::\n").unwrap();
fs::set_permissions(&p, fs::Permissions::from_mode(0o600)).unwrap();
append_lines(&p, &["b:!*:1::::::".into()]).unwrap();
assert_eq!(
fs::metadata(&p).unwrap().permissions().mode() & 0o7777,
0o600
);
assert_eq!(
fs::read_to_string(&p).unwrap(),
"a:!:1::::::\nb:!*:1::::::\n"
);
}
#[test]
fn id_map_missing_is_empty() {
let dir = tempdir();
assert!(load_id_map(&dir.join("nope")).unwrap().is_empty());
}
fn tempdir() -> PathBuf {
let p = std::env::temp_dir().join(format!(
"uil-test-{}-{}",
std::process::id(),
std::time::SystemTime::now()
.duration_since(std::time::UNIX_EPOCH)
.unwrap()
.as_nanos()
));
fs::create_dir_all(&p).unwrap();
p
}
}

View File

@@ -33,6 +33,7 @@ rustPlatform.buildRustPackage (finalAttrs: {
tests = {
inherit (nixosTests)
userborn
userborn-migration
userborn-mutable-users
userborn-mutable-etc
userborn-immutable-users

View File

@@ -9,16 +9,16 @@
rustPlatform.buildRustPackage (finalAttrs: {
pname = "versatiles";
version = "4.6.1";
version = "4.7.0";
src = fetchFromGitHub {
owner = "versatiles-org";
repo = "versatiles-rs";
tag = "v${finalAttrs.version}";
hash = "sha256-J15w0WLewK9E5FVYzMJ1NkiZ9/qbEXxmfX2bM6m+zU8=";
hash = "sha256-WgC5KO6Uz0FQt4Fh08FhZh1RMfDA32Bq70pfMGoDvxU=";
};
cargoHash = "sha256-buVcK5MQrB3Gu7GPKkeofqTrVOv3xXYQd8VlLV5q1u0=";
cargoHash = "sha256-HzTpvnuODTl+fTgYFdbkerquWjjrFw440+pJDGzRnFk=";
nativeBuildInputs = [
pkg-config

View File

@@ -8,13 +8,13 @@
}:
buildGoModule (finalAttrs: {
pname = "ytt";
version = "0.55.1";
version = "0.55.2";
src = fetchFromGitHub {
owner = "carvel-dev";
repo = "ytt";
tag = "v${finalAttrs.version}";
hash = "sha256-HysL71PTCjWxgrqF8Ua7fUtzpxcf/XEbTlek+CvfUxA=";
hash = "sha256-IwM39J5DRCW2CuAmq7Q+KkeqDMLFcktU3NDbBh8wt7g=";
};
vendorHash = null;

View File

@@ -1,58 +0,0 @@
{
lib,
flutter,
fetchFromGitHub,
}:
flutter.buildFlutterApplication rec {
pname = "expidus-calculator";
version = "0.1.1-alpha";
src = fetchFromGitHub {
owner = "ExpidusOS";
repo = "calculator";
rev = version;
hash = "sha256-O3LHp10Fo3PW3zoN7mFSQEKh+AAaR+IqkRtc6nQrIZE=";
};
flutterBuildFlags = [
"--dart-define=COMMIT_HASH=a5d8f54404b9994f83beb367a1cd11e04a6420cb"
];
pubspecLock = lib.importJSON ./pubspec.lock.json;
gitHashes = {
libtokyo = "sha256-T0+vyfSfijLv7MvM+zt3bkVpb3aVrlDnse2xyNMp9GU=";
libtokyo_flutter = "sha256-T0+vyfSfijLv7MvM+zt3bkVpb3aVrlDnse2xyNMp9GU=";
};
postInstall = ''
rm $out/bin/calculator
ln -s $out/app/$pname/calculator $out/bin/expidus-calculator
mkdir -p $out/share/applications
mv $out/app/$pname/data/com.expidusos.calculator.desktop $out/share/applications
mkdir -p $out/share/icons
mv $out/app/$pname/data/com.expidusos.calculator.png $out/share/icons
mkdir -p $out/share/metainfo
mv $out/app/$pname/data/com.expidusos.calculator.metainfo.xml $out/share/metainfo
substituteInPlace "$out/share/applications/com.expidusos.calculator.desktop" \
--replace "Exec=calculator" "Exec=$out/bin/expidus-calculator" \
--replace "Icon=com.expidusos.calculator" "Icon=$out/share/icons/com.expidusos.calculator.png"
'';
meta = {
broken = true;
description = "ExpidusOS Calculator";
homepage = "https://expidusos.com";
license = lib.licenses.gpl3Only;
maintainers = with lib.maintainers; [ RossComputerGuy ];
platforms = [
"x86_64-linux"
"aarch64-linux"
];
mainProgram = "expidus-calculator";
};
}

View File

@@ -1,790 +0,0 @@
{
"packages": {
"args": {
"dependency": "transitive",
"description": {
"name": "args",
"sha256": "eef6c46b622e0494a36c5a12d10d77fb4e855501a91c1b9ef9339326e58f0596",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.4.2"
},
"async": {
"dependency": "transitive",
"description": {
"name": "async",
"sha256": "947bfcf187f74dbc5e146c9eb9c0f10c9f8b30743e341481c1e2ed3ecc18c20c",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.11.0"
},
"bitsdojo_window": {
"dependency": "direct main",
"description": {
"name": "bitsdojo_window",
"sha256": "1118bc1cd16e6f358431ca4473af57cc1b287d2ceab46dfab6d59a9463160622",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.5"
},
"bitsdojo_window_linux": {
"dependency": "transitive",
"description": {
"name": "bitsdojo_window_linux",
"sha256": "d3804a30315fcbb43b28acc86d1180ce0be22c0c738ad2da9e5ade4d8dbd9655",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.3"
},
"bitsdojo_window_macos": {
"dependency": "transitive",
"description": {
"name": "bitsdojo_window_macos",
"sha256": "d2a9886c74516c5b84c1dd65ab8ee5d1c52055b265ebf0e7d664dee28366b521",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.3"
},
"bitsdojo_window_platform_interface": {
"dependency": "transitive",
"description": {
"name": "bitsdojo_window_platform_interface",
"sha256": "65daa015a0c6dba749bdd35a0f092e7a8ba8b0766aa0480eb3ef808086f6e27c",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.2"
},
"bitsdojo_window_windows": {
"dependency": "transitive",
"description": {
"name": "bitsdojo_window_windows",
"sha256": "8766a40aac84a6d7bdcaa716b24997e028fc9a9a1800495fc031721fd5a22ed0",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.5"
},
"boolean_selector": {
"dependency": "transitive",
"description": {
"name": "boolean_selector",
"sha256": "6cfb5af12253eaf2b368f07bacc5a80d1301a071c73360d746b7f2e32d762c66",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.1"
},
"characters": {
"dependency": "transitive",
"description": {
"name": "characters",
"sha256": "04a925763edad70e8443c99234dc3328f442e811f1d8fd1a72f1c8ad0f69a605",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.3.0"
},
"clock": {
"dependency": "transitive",
"description": {
"name": "clock",
"sha256": "cb6d7f03e1de671e34607e909a7213e31d7752be4fb66a86d29fe1eb14bfb5cf",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.1.1"
},
"collection": {
"dependency": "transitive",
"description": {
"name": "collection",
"sha256": "4a07be6cb69c84d677a6c3096fcf960cc3285a8330b4603e0d463d15d9bd934c",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.17.1"
},
"crypto": {
"dependency": "transitive",
"description": {
"name": "crypto",
"sha256": "ff625774173754681d66daaf4a448684fb04b78f902da9cb3d308c19cc5e8bab",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.0.3"
},
"fake_async": {
"dependency": "transitive",
"description": {
"name": "fake_async",
"sha256": "511392330127add0b769b75a987850d136345d9227c6b94c96a04cf4a391bf78",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.3.1"
},
"ffi": {
"dependency": "transitive",
"description": {
"name": "ffi",
"sha256": "7bf0adc28a23d395f19f3f1eb21dd7cfd1dd9f8e1c50051c069122e6853bc878",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.0"
},
"file": {
"dependency": "transitive",
"description": {
"name": "file",
"sha256": "1b92bec4fc2a72f59a8e15af5f52cd441e4a7860b49499d69dfa817af20e925d",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "6.1.4"
},
"filesize": {
"dependency": "transitive",
"description": {
"name": "filesize",
"sha256": "f53df1f27ff60e466eefcd9df239e02d4722d5e2debee92a87dfd99ac66de2af",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.0.1"
},
"flutter": {
"dependency": "direct main",
"description": "flutter",
"source": "sdk",
"version": "0.0.0"
},
"flutter_adaptive_scaffold": {
"dependency": "direct main",
"description": {
"name": "flutter_adaptive_scaffold",
"sha256": "3e78be8b9c95b1c9832b2f8ec4a845adac205c4bb5e7bd3fb204b07990229167",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.7+1"
},
"flutter_lints": {
"dependency": "direct dev",
"description": {
"name": "flutter_lints",
"sha256": "a25a15ebbdfc33ab1cd26c63a6ee519df92338a9c10f122adda92938253bef04",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.0.3"
},
"flutter_localizations": {
"dependency": "direct main",
"description": "flutter",
"source": "sdk",
"version": "0.0.0"
},
"flutter_markdown": {
"dependency": "direct main",
"description": {
"name": "flutter_markdown",
"sha256": "d4a1cb250c4e059586af0235f32e02882860a508e189b61f2b31b8810c1e1330",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.6.17+2"
},
"flutter_test": {
"dependency": "direct dev",
"description": "flutter",
"source": "sdk",
"version": "0.0.0"
},
"flutter_web_plugins": {
"dependency": "transitive",
"description": "flutter",
"source": "sdk",
"version": "0.0.0"
},
"http": {
"dependency": "transitive",
"description": {
"name": "http",
"sha256": "5895291c13fa8a3bd82e76d5627f69e0d85ca6a30dcac95c4ea19a5d555879c2",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.13.6"
},
"http_parser": {
"dependency": "transitive",
"description": {
"name": "http_parser",
"sha256": "2aa08ce0341cc9b354a498388e30986515406668dbcc4f7c950c3e715496693b",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "4.0.2"
},
"intl": {
"dependency": "transitive",
"description": {
"name": "intl",
"sha256": "a3715e3bc90294e971cb7dc063fbf3cd9ee0ebf8604ffeafabd9e6f16abbdbe6",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.18.0"
},
"js": {
"dependency": "transitive",
"description": {
"name": "js",
"sha256": "f2c445dce49627136094980615a031419f7f3eb393237e4ecd97ac15dea343f3",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.6.7"
},
"libtokyo": {
"dependency": "direct main",
"description": {
"path": "packages/libtokyo",
"ref": "f48d528ebfc22fe827fe9f2d1965be1d339ccfb7",
"resolved-ref": "f48d528ebfc22fe827fe9f2d1965be1d339ccfb7",
"url": "https://github.com/ExpidusOS/libtokyo.git"
},
"source": "git",
"version": "0.1.0"
},
"libtokyo_flutter": {
"dependency": "direct main",
"description": {
"path": "packages/libtokyo_flutter",
"ref": "f48d528ebfc22fe827fe9f2d1965be1d339ccfb7",
"resolved-ref": "f48d528ebfc22fe827fe9f2d1965be1d339ccfb7",
"url": "https://github.com/ExpidusOS/libtokyo.git"
},
"source": "git",
"version": "0.1.0"
},
"lints": {
"dependency": "transitive",
"description": {
"name": "lints",
"sha256": "0a217c6c989d21039f1498c3ed9f3ed71b354e69873f13a8dfc3c9fe76f1b452",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.1"
},
"markdown": {
"dependency": "direct main",
"description": {
"name": "markdown",
"sha256": "acf35edccc0463a9d7384e437c015a3535772e09714cf60e07eeef3a15870dcd",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "7.1.1"
},
"matcher": {
"dependency": "transitive",
"description": {
"name": "matcher",
"sha256": "6501fbd55da300384b768785b83e5ce66991266cec21af89ab9ae7f5ce1c4cbb",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.12.15"
},
"material_color_utilities": {
"dependency": "transitive",
"description": {
"name": "material_color_utilities",
"sha256": "d92141dc6fe1dad30722f9aa826c7fbc896d021d792f80678280601aff8cf724",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.2.0"
},
"material_theme_builder": {
"dependency": "transitive",
"description": {
"name": "material_theme_builder",
"sha256": "380ab70835e01f4ee0c37904eebae9e36ed37b5cf8ed40d67412ea3244a2afd6",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.0.4"
},
"math_expressions": {
"dependency": "direct main",
"description": {
"name": "math_expressions",
"sha256": "3576593617c3870d75728a751f6ec6e606706d44e363f088ac394b5a28a98064",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.4.0"
},
"meta": {
"dependency": "transitive",
"description": {
"name": "meta",
"sha256": "3c74dbf8763d36539f114c799d8a2d87343b5067e9d796ca22b5eb8437090ee3",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.9.1"
},
"nested": {
"dependency": "transitive",
"description": {
"name": "nested",
"sha256": "03bac4c528c64c95c722ec99280375a6f2fc708eec17c7b3f07253b626cd2a20",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.0.0"
},
"package_info_plus": {
"dependency": "direct main",
"description": {
"name": "package_info_plus",
"sha256": "10259b111176fba5c505b102e3a5b022b51dd97e30522e906d6922c745584745",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.1.2"
},
"package_info_plus_platform_interface": {
"dependency": "transitive",
"description": {
"name": "package_info_plus_platform_interface",
"sha256": "9bc8ba46813a4cc42c66ab781470711781940780fd8beddd0c3da62506d3a6c6",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.0.1"
},
"path": {
"dependency": "transitive",
"description": {
"name": "path",
"sha256": "8829d8a55c13fc0e37127c29fedf290c102f4e40ae94ada574091fe0ff96c917",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.8.3"
},
"path_provider_linux": {
"dependency": "transitive",
"description": {
"name": "path_provider_linux",
"sha256": "f7a1fe3a634fe7734c8d3f2766ad746ae2a2884abe22e241a8b301bf5cac3279",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.2.1"
},
"path_provider_platform_interface": {
"dependency": "transitive",
"description": {
"name": "path_provider_platform_interface",
"sha256": "94b1e0dd80970c1ce43d5d4e050a9918fce4f4a775e6142424c30a29a363265c",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.1"
},
"path_provider_windows": {
"dependency": "transitive",
"description": {
"name": "path_provider_windows",
"sha256": "8bc9f22eee8690981c22aa7fc602f5c85b497a6fb2ceb35ee5a5e5ed85ad8170",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.2.1"
},
"platform": {
"dependency": "transitive",
"description": {
"name": "platform",
"sha256": "ae68c7bfcd7383af3629daafb32fb4e8681c7154428da4febcff06200585f102",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.1.2"
},
"plugin_platform_interface": {
"dependency": "transitive",
"description": {
"name": "plugin_platform_interface",
"sha256": "da3fdfeccc4d4ff2da8f8c556704c08f912542c5fb3cf2233ed75372384a034d",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.6"
},
"provider": {
"dependency": "direct main",
"description": {
"name": "provider",
"sha256": "cdbe7530b12ecd9eb455bdaa2fcb8d4dad22e80b8afb4798b41479d5ce26847f",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "6.0.5"
},
"pub_semver": {
"dependency": "direct main",
"description": {
"name": "pub_semver",
"sha256": "40d3ab1bbd474c4c2328c91e3a7df8c6dd629b79ece4c4bd04bee496a224fb0c",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.4"
},
"pubspec": {
"dependency": "direct main",
"description": {
"name": "pubspec",
"sha256": "f534a50a2b4d48dc3bc0ec147c8bd7c304280fff23b153f3f11803c4d49d927e",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.3.0"
},
"quiver": {
"dependency": "transitive",
"description": {
"name": "quiver",
"sha256": "b1c1ac5ce6688d77f65f3375a9abb9319b3cb32486bdc7a1e0fdf004d7ba4e47",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.2.1"
},
"sentry": {
"dependency": "transitive",
"description": {
"name": "sentry",
"sha256": "39c23342fc96105da449914f7774139a17a0ca8a4e70d9ad5200171f7e47d6ba",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "7.9.0"
},
"sentry_flutter": {
"dependency": "direct main",
"description": {
"name": "sentry_flutter",
"sha256": "ff68ab31918690da004a42e20204242a3ad9ad57da7e2712da8487060ac9767f",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "7.9.0"
},
"shared_preferences": {
"dependency": "direct main",
"description": {
"name": "shared_preferences",
"sha256": "b7f41bad7e521d205998772545de63ff4e6c97714775902c199353f8bf1511ac",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.2.1"
},
"shared_preferences_android": {
"dependency": "transitive",
"description": {
"name": "shared_preferences_android",
"sha256": "8568a389334b6e83415b6aae55378e158fbc2314e074983362d20c562780fb06",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.2.1"
},
"shared_preferences_foundation": {
"dependency": "transitive",
"description": {
"name": "shared_preferences_foundation",
"sha256": "7bf53a9f2d007329ee6f3df7268fd498f8373602f943c975598bbb34649b62a7",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.3.4"
},
"shared_preferences_linux": {
"dependency": "transitive",
"description": {
"name": "shared_preferences_linux",
"sha256": "c2eb5bf57a2fe9ad6988121609e47d3e07bb3bdca5b6f8444e4cf302428a128a",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.3.1"
},
"shared_preferences_platform_interface": {
"dependency": "transitive",
"description": {
"name": "shared_preferences_platform_interface",
"sha256": "d4ec5fc9ebb2f2e056c617112aa75dcf92fc2e4faaf2ae999caa297473f75d8a",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.3.1"
},
"shared_preferences_web": {
"dependency": "transitive",
"description": {
"name": "shared_preferences_web",
"sha256": "d762709c2bbe80626ecc819143013cc820fa49ca5e363620ee20a8b15a3e3daf",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.2.1"
},
"shared_preferences_windows": {
"dependency": "transitive",
"description": {
"name": "shared_preferences_windows",
"sha256": "f763a101313bd3be87edffe0560037500967de9c394a714cd598d945517f694f",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.3.1"
},
"sky_engine": {
"dependency": "transitive",
"description": "flutter",
"source": "sdk",
"version": "0.0.99"
},
"source_span": {
"dependency": "transitive",
"description": {
"name": "source_span",
"sha256": "dd904f795d4b4f3b870833847c461801f6750a9fa8e61ea5ac53f9422b31f250",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.9.1"
},
"stack_trace": {
"dependency": "transitive",
"description": {
"name": "stack_trace",
"sha256": "c3c7d8edb15bee7f0f74debd4b9c5f3c2ea86766fe4178eb2a18eb30a0bdaed5",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.11.0"
},
"stream_channel": {
"dependency": "transitive",
"description": {
"name": "stream_channel",
"sha256": "83615bee9045c1d322bbbd1ba209b7a749c2cbcdcb3fdd1df8eb488b3279c1c8",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.1"
},
"string_scanner": {
"dependency": "transitive",
"description": {
"name": "string_scanner",
"sha256": "556692adab6cfa87322a115640c11f13cb77b3f076ddcc5d6ae3c20242bedcde",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.2.0"
},
"term_glyph": {
"dependency": "transitive",
"description": {
"name": "term_glyph",
"sha256": "a29248a84fbb7c79282b40b8c72a1209db169a2e0542bce341da992fe1bc7e84",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.2.1"
},
"test_api": {
"dependency": "transitive",
"description": {
"name": "test_api",
"sha256": "eb6ac1540b26de412b3403a163d919ba86f6a973fe6cc50ae3541b80092fdcfb",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.5.1"
},
"typed_data": {
"dependency": "transitive",
"description": {
"name": "typed_data",
"sha256": "facc8d6582f16042dd49f2463ff1bd6e2c9ef9f3d5da3d9b087e244a7b564b3c",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.3.2"
},
"uri": {
"dependency": "transitive",
"description": {
"name": "uri",
"sha256": "889eea21e953187c6099802b7b4cf5219ba8f3518f604a1033064d45b1b8268a",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.0.0"
},
"url_launcher": {
"dependency": "direct main",
"description": {
"name": "url_launcher",
"sha256": "47e208a6711459d813ba18af120d9663c20bdf6985d6ad39fe165d2538378d27",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "6.1.14"
},
"url_launcher_android": {
"dependency": "transitive",
"description": {
"name": "url_launcher_android",
"sha256": "b04af59516ab45762b2ca6da40fa830d72d0f6045cd97744450b73493fa76330",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "6.1.0"
},
"url_launcher_ios": {
"dependency": "transitive",
"description": {
"name": "url_launcher_ios",
"sha256": "7c65021d5dee51813d652357bc65b8dd4a6177082a9966bc8ba6ee477baa795f",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "6.1.5"
},
"url_launcher_linux": {
"dependency": "transitive",
"description": {
"name": "url_launcher_linux",
"sha256": "b651aad005e0cb06a01dbd84b428a301916dc75f0e7ea6165f80057fee2d8e8e",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.0.6"
},
"url_launcher_macos": {
"dependency": "transitive",
"description": {
"name": "url_launcher_macos",
"sha256": "b55486791f666e62e0e8ff825e58a023fd6b1f71c49926483f1128d3bbd8fe88",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.0.7"
},
"url_launcher_platform_interface": {
"dependency": "transitive",
"description": {
"name": "url_launcher_platform_interface",
"sha256": "95465b39f83bfe95fcb9d174829d6476216f2d548b79c38ab2506e0458787618",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.5"
},
"url_launcher_web": {
"dependency": "transitive",
"description": {
"name": "url_launcher_web",
"sha256": "ba140138558fcc3eead51a1c42e92a9fb074a1b1149ed3c73e66035b2ccd94f2",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.0.19"
},
"url_launcher_windows": {
"dependency": "transitive",
"description": {
"name": "url_launcher_windows",
"sha256": "95fef3129dc7cfaba2bc3d5ba2e16063bb561fc6d78e63eee16162bc70029069",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.0.8"
},
"uuid": {
"dependency": "transitive",
"description": {
"name": "uuid",
"sha256": "648e103079f7c64a36dc7d39369cabb358d377078a051d6ae2ad3aa539519313",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.0.7"
},
"vector_math": {
"dependency": "transitive",
"description": {
"name": "vector_math",
"sha256": "80b3257d1492ce4d091729e3a67a60407d227c27241d6927be0130c98e741803",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.4"
},
"win32": {
"dependency": "transitive",
"description": {
"name": "win32",
"sha256": "a6f0236dbda0f63aa9a25ad1ff9a9d8a4eaaa5012da0dc59d21afdb1dc361ca4",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.1.4"
},
"xdg_directories": {
"dependency": "transitive",
"description": {
"name": "xdg_directories",
"sha256": "589ada45ba9e39405c198fe34eb0f607cddb2108527e658136120892beac46d2",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.0.3"
},
"yaml": {
"dependency": "transitive",
"description": {
"name": "yaml",
"sha256": "75769501ea3489fca56601ff33454fe45507ea3bfb014161abc3b43ae25989d5",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.1.2"
}
},
"sdks": {
"dart": ">=3.0.5 <4.0.0",
"flutter": ">=3.10.0"
}
}

View File

@@ -1,10 +0,0 @@
{ callPackage, flutterPackages }:
{
calculator = callPackage ./calculator {
flutter = flutterPackages.v3_35;
};
file-manager = callPackage ./file-manager {
flutter = flutterPackages.v3_35;
};
}

View File

@@ -1,58 +0,0 @@
{
lib,
flutter,
fetchFromGitHub,
}:
flutter.buildFlutterApplication rec {
pname = "expidus-file-manager";
version = "0.2.1";
src = fetchFromGitHub {
owner = "ExpidusOS";
repo = "file-manager";
rev = version;
hash = "sha256-R6eszy4Dz8tAPRTwZzRiZWIgVMiGv5zlhFB/HcD6gqg=";
};
flutterBuildFlags = [
"--dart-define=COMMIT_HASH=b4181b9cff18a07e958c81d8f41840d2d36a6705"
];
pubspecLock = lib.importJSON ./pubspec.lock.json;
gitHashes = {
libtokyo = "sha256-T0+vyfSfijLv7MvM+zt3bkVpb3aVrlDnse2xyNMp9GU=";
libtokyo_flutter = "sha256-T0+vyfSfijLv7MvM+zt3bkVpb3aVrlDnse2xyNMp9GU=";
};
postInstall = ''
rm $out/bin/file_manager
ln -s $out/app/$pname/file_manager $out/bin/expidus-file-manager
mkdir -p $out/share/applications
mv $out/app/$pname/data/com.expidusos.file_manager.desktop $out/share/applications
mkdir -p $out/share/icons
mv $out/app/$pname/data/com.expidusos.file_manager.png $out/share/icons
mkdir -p $out/share/metainfo
mv $out/app/$pname/data/com.expidusos.file_manager.metainfo.xml $out/share/metainfo
substituteInPlace "$out/share/applications/com.expidusos.file_manager.desktop" \
--replace "Exec=file_manager" "Exec=$out/bin/expidus-file-manager" \
--replace "Icon=com.expidusos.file_manager" "Icon=$out/share/icons/com.expidusos.file_manager.png"
'';
meta = {
broken = true;
description = "ExpidusOS File Manager";
homepage = "https://expidusos.com";
license = lib.licenses.gpl3;
maintainers = with lib.maintainers; [ RossComputerGuy ];
platforms = [
"x86_64-linux"
"aarch64-linux"
];
mainProgram = "expidus-file-manager";
};
}

View File

@@ -1,910 +0,0 @@
{
"packages": {
"args": {
"dependency": "transitive",
"description": {
"name": "args",
"sha256": "eef6c46b622e0494a36c5a12d10d77fb4e855501a91c1b9ef9339326e58f0596",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.4.2"
},
"async": {
"dependency": "transitive",
"description": {
"name": "async",
"sha256": "947bfcf187f74dbc5e146c9eb9c0f10c9f8b30743e341481c1e2ed3ecc18c20c",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.11.0"
},
"bitsdojo_window": {
"dependency": "direct main",
"description": {
"name": "bitsdojo_window",
"sha256": "1118bc1cd16e6f358431ca4473af57cc1b287d2ceab46dfab6d59a9463160622",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.5"
},
"bitsdojo_window_linux": {
"dependency": "transitive",
"description": {
"name": "bitsdojo_window_linux",
"sha256": "d3804a30315fcbb43b28acc86d1180ce0be22c0c738ad2da9e5ade4d8dbd9655",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.3"
},
"bitsdojo_window_macos": {
"dependency": "transitive",
"description": {
"name": "bitsdojo_window_macos",
"sha256": "d2a9886c74516c5b84c1dd65ab8ee5d1c52055b265ebf0e7d664dee28366b521",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.3"
},
"bitsdojo_window_platform_interface": {
"dependency": "transitive",
"description": {
"name": "bitsdojo_window_platform_interface",
"sha256": "65daa015a0c6dba749bdd35a0f092e7a8ba8b0766aa0480eb3ef808086f6e27c",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.2"
},
"bitsdojo_window_windows": {
"dependency": "transitive",
"description": {
"name": "bitsdojo_window_windows",
"sha256": "8766a40aac84a6d7bdcaa716b24997e028fc9a9a1800495fc031721fd5a22ed0",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.5"
},
"boolean_selector": {
"dependency": "transitive",
"description": {
"name": "boolean_selector",
"sha256": "6cfb5af12253eaf2b368f07bacc5a80d1301a071c73360d746b7f2e32d762c66",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.1"
},
"characters": {
"dependency": "transitive",
"description": {
"name": "characters",
"sha256": "04a925763edad70e8443c99234dc3328f442e811f1d8fd1a72f1c8ad0f69a605",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.3.0"
},
"clock": {
"dependency": "transitive",
"description": {
"name": "clock",
"sha256": "cb6d7f03e1de671e34607e909a7213e31d7752be4fb66a86d29fe1eb14bfb5cf",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.1.1"
},
"collection": {
"dependency": "direct main",
"description": {
"name": "collection",
"sha256": "f092b211a4319e98e5ff58223576de6c2803db36221657b46c82574721240687",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.17.2"
},
"crypto": {
"dependency": "transitive",
"description": {
"name": "crypto",
"sha256": "ff625774173754681d66daaf4a448684fb04b78f902da9cb3d308c19cc5e8bab",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.0.3"
},
"dbus": {
"dependency": "transitive",
"description": {
"name": "dbus",
"sha256": "6f07cba3f7b3448d42d015bfd3d53fe12e5b36da2423f23838efc1d5fb31a263",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.7.8"
},
"fake_async": {
"dependency": "transitive",
"description": {
"name": "fake_async",
"sha256": "511392330127add0b769b75a987850d136345d9227c6b94c96a04cf4a391bf78",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.3.1"
},
"ffi": {
"dependency": "direct main",
"description": {
"name": "ffi",
"sha256": "7bf0adc28a23d395f19f3f1eb21dd7cfd1dd9f8e1c50051c069122e6853bc878",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.0"
},
"file": {
"dependency": "transitive",
"description": {
"name": "file",
"sha256": "1b92bec4fc2a72f59a8e15af5f52cd441e4a7860b49499d69dfa817af20e925d",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "6.1.4"
},
"filesize": {
"dependency": "direct main",
"description": {
"name": "filesize",
"sha256": "f53df1f27ff60e466eefcd9df239e02d4722d5e2debee92a87dfd99ac66de2af",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.0.1"
},
"flutter": {
"dependency": "direct main",
"description": "flutter",
"source": "sdk",
"version": "0.0.0"
},
"flutter_adaptive_scaffold": {
"dependency": "direct main",
"description": {
"name": "flutter_adaptive_scaffold",
"sha256": "4f448902314bc9b6cf820c85d5bad4de6489c0eff75dcedf5098f3a53ec981ee",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.6"
},
"flutter_lints": {
"dependency": "direct dev",
"description": {
"name": "flutter_lints",
"sha256": "2118df84ef0c3ca93f96123a616ae8540879991b8b57af2f81b76a7ada49b2a4",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.0.2"
},
"flutter_localizations": {
"dependency": "direct main",
"description": "flutter",
"source": "sdk",
"version": "0.0.0"
},
"flutter_markdown": {
"dependency": "direct main",
"description": {
"name": "flutter_markdown",
"sha256": "2b206d397dd7836ea60035b2d43825c8a303a76a5098e66f42d55a753e18d431",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.6.17+1"
},
"flutter_test": {
"dependency": "direct dev",
"description": "flutter",
"source": "sdk",
"version": "0.0.0"
},
"flutter_web_plugins": {
"dependency": "transitive",
"description": "flutter",
"source": "sdk",
"version": "0.0.0"
},
"http": {
"dependency": "transitive",
"description": {
"name": "http",
"sha256": "5895291c13fa8a3bd82e76d5627f69e0d85ca6a30dcac95c4ea19a5d555879c2",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.13.6"
},
"http_parser": {
"dependency": "transitive",
"description": {
"name": "http_parser",
"sha256": "2aa08ce0341cc9b354a498388e30986515406668dbcc4f7c950c3e715496693b",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "4.0.2"
},
"intl": {
"dependency": "direct main",
"description": {
"name": "intl",
"sha256": "3bc132a9dbce73a7e4a21a17d06e1878839ffbf975568bc875c60537824b0c4d",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.18.1"
},
"libtokyo": {
"dependency": "direct main",
"description": {
"path": "packages/libtokyo",
"ref": "f48d528ebfc22fe827fe9f2d1965be1d339ccfb7",
"resolved-ref": "f48d528ebfc22fe827fe9f2d1965be1d339ccfb7",
"url": "https://github.com/ExpidusOS/libtokyo.git"
},
"source": "git",
"version": "0.1.0"
},
"libtokyo_flutter": {
"dependency": "direct main",
"description": {
"path": "packages/libtokyo_flutter",
"ref": "f48d528ebfc22fe827fe9f2d1965be1d339ccfb7",
"resolved-ref": "f48d528ebfc22fe827fe9f2d1965be1d339ccfb7",
"url": "https://github.com/ExpidusOS/libtokyo.git"
},
"source": "git",
"version": "0.1.0"
},
"lints": {
"dependency": "transitive",
"description": {
"name": "lints",
"sha256": "0a217c6c989d21039f1498c3ed9f3ed71b354e69873f13a8dfc3c9fe76f1b452",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.1"
},
"markdown": {
"dependency": "transitive",
"description": {
"name": "markdown",
"sha256": "acf35edccc0463a9d7384e437c015a3535772e09714cf60e07eeef3a15870dcd",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "7.1.1"
},
"matcher": {
"dependency": "transitive",
"description": {
"name": "matcher",
"sha256": "1803e76e6653768d64ed8ff2e1e67bea3ad4b923eb5c56a295c3e634bad5960e",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.12.16"
},
"material_color_utilities": {
"dependency": "transitive",
"description": {
"name": "material_color_utilities",
"sha256": "9528f2f296073ff54cb9fee677df673ace1218163c3bc7628093e7eed5203d41",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.5.0"
},
"material_theme_builder": {
"dependency": "transitive",
"description": {
"name": "material_theme_builder",
"sha256": "380ab70835e01f4ee0c37904eebae9e36ed37b5cf8ed40d67412ea3244a2afd6",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.0.4"
},
"meta": {
"dependency": "transitive",
"description": {
"name": "meta",
"sha256": "3c74dbf8763d36539f114c799d8a2d87343b5067e9d796ca22b5eb8437090ee3",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.9.1"
},
"nested": {
"dependency": "transitive",
"description": {
"name": "nested",
"sha256": "03bac4c528c64c95c722ec99280375a6f2fc708eec17c7b3f07253b626cd2a20",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.0.0"
},
"open_file_plus": {
"dependency": "direct main",
"description": {
"name": "open_file_plus",
"sha256": "f087e32722ffe4bac71925e7a1a9848a1008fd789e47c6628da3ed7845922227",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.4.1"
},
"package_info_plus": {
"dependency": "direct main",
"description": {
"name": "package_info_plus",
"sha256": "10259b111176fba5c505b102e3a5b022b51dd97e30522e906d6922c745584745",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.1.2"
},
"package_info_plus_platform_interface": {
"dependency": "transitive",
"description": {
"name": "package_info_plus_platform_interface",
"sha256": "9bc8ba46813a4cc42c66ab781470711781940780fd8beddd0c3da62506d3a6c6",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.0.1"
},
"path": {
"dependency": "direct main",
"description": {
"name": "path",
"sha256": "8829d8a55c13fc0e37127c29fedf290c102f4e40ae94ada574091fe0ff96c917",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.8.3"
},
"path_provider": {
"dependency": "direct main",
"description": {
"name": "path_provider",
"sha256": "909b84830485dbcd0308edf6f7368bc8fd76afa26a270420f34cabea2a6467a0",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.0"
},
"path_provider_android": {
"dependency": "transitive",
"description": {
"name": "path_provider_android",
"sha256": "5d44fc3314d969b84816b569070d7ace0f1dea04bd94a83f74c4829615d22ad8",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.0"
},
"path_provider_foundation": {
"dependency": "transitive",
"description": {
"name": "path_provider_foundation",
"sha256": "1b744d3d774e5a879bb76d6cd1ecee2ba2c6960c03b1020cd35212f6aa267ac5",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.3.0"
},
"path_provider_linux": {
"dependency": "transitive",
"description": {
"name": "path_provider_linux",
"sha256": "ba2b77f0c52a33db09fc8caf85b12df691bf28d983e84cf87ff6d693cfa007b3",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.2.0"
},
"path_provider_platform_interface": {
"dependency": "direct main",
"description": {
"name": "path_provider_platform_interface",
"sha256": "bced5679c7df11190e1ddc35f3222c858f328fff85c3942e46e7f5589bf9eb84",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.0"
},
"path_provider_windows": {
"dependency": "direct main",
"description": {
"name": "path_provider_windows",
"sha256": "ee0e0d164516b90ae1f970bdf29f726f1aa730d7cfc449ecc74c495378b705da",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.2.0"
},
"permission_handler": {
"dependency": "direct main",
"description": {
"name": "permission_handler",
"sha256": "63e5216aae014a72fe9579ccd027323395ce7a98271d9defa9d57320d001af81",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "10.4.3"
},
"permission_handler_android": {
"dependency": "transitive",
"description": {
"name": "permission_handler_android",
"sha256": "2ffaf52a21f64ac9b35fe7369bb9533edbd4f698e5604db8645b1064ff4cf221",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "10.3.3"
},
"permission_handler_apple": {
"dependency": "transitive",
"description": {
"name": "permission_handler_apple",
"sha256": "99e220bce3f8877c78e4ace901082fb29fa1b4ebde529ad0932d8d664b34f3f5",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "9.1.4"
},
"permission_handler_platform_interface": {
"dependency": "transitive",
"description": {
"name": "permission_handler_platform_interface",
"sha256": "7c6b1500385dd1d2ca61bb89e2488ca178e274a69144d26bbd65e33eae7c02a9",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.11.3"
},
"permission_handler_windows": {
"dependency": "transitive",
"description": {
"name": "permission_handler_windows",
"sha256": "cc074aace208760f1eee6aa4fae766b45d947df85bc831cde77009cdb4720098",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.3"
},
"petitparser": {
"dependency": "transitive",
"description": {
"name": "petitparser",
"sha256": "cb3798bef7fc021ac45b308f4b51208a152792445cce0448c9a4ba5879dd8750",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "5.4.0"
},
"platform": {
"dependency": "transitive",
"description": {
"name": "platform",
"sha256": "4a451831508d7d6ca779f7ac6e212b4023dd5a7d08a27a63da33756410e32b76",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.1.0"
},
"plugin_platform_interface": {
"dependency": "transitive",
"description": {
"name": "plugin_platform_interface",
"sha256": "43798d895c929056255600343db8f049921cbec94d31ec87f1dc5c16c01935dd",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.5"
},
"provider": {
"dependency": "direct main",
"description": {
"name": "provider",
"sha256": "cdbe7530b12ecd9eb455bdaa2fcb8d4dad22e80b8afb4798b41479d5ce26847f",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "6.0.5"
},
"pub_semver": {
"dependency": "direct main",
"description": {
"name": "pub_semver",
"sha256": "40d3ab1bbd474c4c2328c91e3a7df8c6dd629b79ece4c4bd04bee496a224fb0c",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.4"
},
"pubspec": {
"dependency": "direct main",
"description": {
"name": "pubspec",
"sha256": "f534a50a2b4d48dc3bc0ec147c8bd7c304280fff23b153f3f11803c4d49d927e",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.3.0"
},
"quiver": {
"dependency": "transitive",
"description": {
"name": "quiver",
"sha256": "b1c1ac5ce6688d77f65f3375a9abb9319b3cb32486bdc7a1e0fdf004d7ba4e47",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.2.1"
},
"sentry": {
"dependency": "transitive",
"description": {
"name": "sentry",
"sha256": "39c23342fc96105da449914f7774139a17a0ca8a4e70d9ad5200171f7e47d6ba",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "7.9.0"
},
"sentry_flutter": {
"dependency": "direct main",
"description": {
"name": "sentry_flutter",
"sha256": "ff68ab31918690da004a42e20204242a3ad9ad57da7e2712da8487060ac9767f",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "7.9.0"
},
"shared_preferences": {
"dependency": "direct main",
"description": {
"name": "shared_preferences",
"sha256": "0344316c947ffeb3a529eac929e1978fcd37c26be4e8468628bac399365a3ca1",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.2.0"
},
"shared_preferences_android": {
"dependency": "transitive",
"description": {
"name": "shared_preferences_android",
"sha256": "fe8401ec5b6dcd739a0fe9588802069e608c3fdbfd3c3c93e546cf2f90438076",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.2.0"
},
"shared_preferences_foundation": {
"dependency": "transitive",
"description": {
"name": "shared_preferences_foundation",
"sha256": "f39696b83e844923b642ce9dd4bd31736c17e697f6731a5adf445b1274cf3cd4",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.3.2"
},
"shared_preferences_linux": {
"dependency": "transitive",
"description": {
"name": "shared_preferences_linux",
"sha256": "71d6806d1449b0a9d4e85e0c7a917771e672a3d5dc61149cc9fac871115018e1",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.3.0"
},
"shared_preferences_platform_interface": {
"dependency": "transitive",
"description": {
"name": "shared_preferences_platform_interface",
"sha256": "23b052f17a25b90ff2b61aad4cc962154da76fb62848a9ce088efe30d7c50ab1",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.3.0"
},
"shared_preferences_web": {
"dependency": "transitive",
"description": {
"name": "shared_preferences_web",
"sha256": "7347b194fb0bbeb4058e6a4e87ee70350b6b2b90f8ac5f8bd5b3a01548f6d33a",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.2.0"
},
"shared_preferences_windows": {
"dependency": "transitive",
"description": {
"name": "shared_preferences_windows",
"sha256": "f95e6a43162bce43c9c3405f3eb6f39e5b5d11f65fab19196cf8225e2777624d",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.3.0"
},
"sky_engine": {
"dependency": "transitive",
"description": "flutter",
"source": "sdk",
"version": "0.0.99"
},
"source_span": {
"dependency": "transitive",
"description": {
"name": "source_span",
"sha256": "53e943d4206a5e30df338fd4c6e7a077e02254531b138a15aec3bd143c1a8b3c",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.10.0"
},
"stack_trace": {
"dependency": "transitive",
"description": {
"name": "stack_trace",
"sha256": "c3c7d8edb15bee7f0f74debd4b9c5f3c2ea86766fe4178eb2a18eb30a0bdaed5",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.11.0"
},
"stream_channel": {
"dependency": "transitive",
"description": {
"name": "stream_channel",
"sha256": "83615bee9045c1d322bbbd1ba209b7a749c2cbcdcb3fdd1df8eb488b3279c1c8",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.1"
},
"string_scanner": {
"dependency": "transitive",
"description": {
"name": "string_scanner",
"sha256": "556692adab6cfa87322a115640c11f13cb77b3f076ddcc5d6ae3c20242bedcde",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.2.0"
},
"term_glyph": {
"dependency": "transitive",
"description": {
"name": "term_glyph",
"sha256": "a29248a84fbb7c79282b40b8c72a1209db169a2e0542bce341da992fe1bc7e84",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.2.1"
},
"test_api": {
"dependency": "transitive",
"description": {
"name": "test_api",
"sha256": "75760ffd7786fffdfb9597c35c5b27eaeec82be8edfb6d71d32651128ed7aab8",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.6.0"
},
"typed_data": {
"dependency": "transitive",
"description": {
"name": "typed_data",
"sha256": "facc8d6582f16042dd49f2463ff1bd6e2c9ef9f3d5da3d9b087e244a7b564b3c",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.3.2"
},
"udisks": {
"dependency": "direct main",
"description": {
"name": "udisks",
"sha256": "847144fb868b9e3602895e89f438f77c2a4fda9e4b02f7d368dc1d2c6a40b475",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.4.0"
},
"uri": {
"dependency": "transitive",
"description": {
"name": "uri",
"sha256": "889eea21e953187c6099802b7b4cf5219ba8f3518f604a1033064d45b1b8268a",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.0.0"
},
"url_launcher": {
"dependency": "direct main",
"description": {
"name": "url_launcher",
"sha256": "781bd58a1eb16069412365c98597726cd8810ae27435f04b3b4d3a470bacd61e",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "6.1.12"
},
"url_launcher_android": {
"dependency": "transitive",
"description": {
"name": "url_launcher_android",
"sha256": "3dd2388cc0c42912eee04434531a26a82512b9cb1827e0214430c9bcbddfe025",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "6.0.38"
},
"url_launcher_ios": {
"dependency": "transitive",
"description": {
"name": "url_launcher_ios",
"sha256": "9af7ea73259886b92199f9e42c116072f05ff9bea2dcb339ab935dfc957392c2",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "6.1.4"
},
"url_launcher_linux": {
"dependency": "transitive",
"description": {
"name": "url_launcher_linux",
"sha256": "207f4ddda99b95b4d4868320a352d374b0b7e05eefad95a4a26f57da413443f5",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.0.5"
},
"url_launcher_macos": {
"dependency": "transitive",
"description": {
"name": "url_launcher_macos",
"sha256": "1c4fdc0bfea61a70792ce97157e5cc17260f61abbe4f39354513f39ec6fd73b1",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.0.6"
},
"url_launcher_platform_interface": {
"dependency": "transitive",
"description": {
"name": "url_launcher_platform_interface",
"sha256": "bfdfa402f1f3298637d71ca8ecfe840b4696698213d5346e9d12d4ab647ee2ea",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.3"
},
"url_launcher_web": {
"dependency": "transitive",
"description": {
"name": "url_launcher_web",
"sha256": "cc26720eefe98c1b71d85f9dc7ef0cada5132617046369d9dc296b3ecaa5cbb4",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.0.18"
},
"url_launcher_windows": {
"dependency": "transitive",
"description": {
"name": "url_launcher_windows",
"sha256": "7967065dd2b5fccc18c653b97958fdf839c5478c28e767c61ee879f4e7882422",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.0.7"
},
"uuid": {
"dependency": "transitive",
"description": {
"name": "uuid",
"sha256": "648e103079f7c64a36dc7d39369cabb358d377078a051d6ae2ad3aa539519313",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.0.7"
},
"vector_math": {
"dependency": "transitive",
"description": {
"name": "vector_math",
"sha256": "80b3257d1492ce4d091729e3a67a60407d227c27241d6927be0130c98e741803",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "2.1.4"
},
"web": {
"dependency": "transitive",
"description": {
"name": "web",
"sha256": "dc8ccd225a2005c1be616fe02951e2e342092edf968cf0844220383757ef8f10",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "0.1.4-beta"
},
"win32": {
"dependency": "direct main",
"description": {
"name": "win32",
"sha256": "a6f0236dbda0f63aa9a25ad1ff9a9d8a4eaaa5012da0dc59d21afdb1dc361ca4",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.1.4"
},
"xdg_directories": {
"dependency": "direct main",
"description": {
"name": "xdg_directories",
"sha256": "f0c26453a2d47aa4c2570c6a033246a3fc62da2fe23c7ffdd0a7495086dc0247",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "1.0.2"
},
"xml": {
"dependency": "transitive",
"description": {
"name": "xml",
"sha256": "5bc72e1e45e941d825fd7468b9b4cc3b9327942649aeb6fc5cdbf135f0a86e84",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "6.3.0"
},
"yaml": {
"dependency": "transitive",
"description": {
"name": "yaml",
"sha256": "75769501ea3489fca56601ff33454fe45507ea3bfb014161abc3b43ae25989d5",
"url": "https://pub.dev"
},
"source": "hosted",
"version": "3.1.2"
}
},
"sdks": {
"dart": ">=3.1.0-185.0.dev <4.0.0",
"flutter": ">=3.10.0"
}
}

View File

@@ -158,6 +158,8 @@ lib.extendMkDerivation {
};
in
{
inherit universal;
linux = universal // {
outputs = universal.outputs or [ ] ++ [ "debug" ];

View File

@@ -1,5 +1,4 @@
{
useNixpkgsEngine ? false,
callPackage,
fetchzip,
fetchFromGitHub,
@@ -22,10 +21,6 @@ let
{
version,
engineVersion,
engineSwiftShaderHash,
engineSwiftShaderRev,
engineHashes,
enginePatches,
dartVersion,
flutterHash,
dartHash,
@@ -39,14 +34,9 @@ let
inherit
version
engineVersion
engineSwiftShaderRev
engineSwiftShaderHash
engineHashes
enginePatches
patches
pubspecLock
artifactHashes
useNixpkgsEngine
channel
;
@@ -123,7 +113,6 @@ let
mkFlutter (
{
patches = (getPatches ./patches) ++ (getPatches (versionDir + "/patches"));
enginePatches = (getPatches ./engine/patches) ++ (getPatches (versionDir + "/engine/patches"));
}
// data
)

View File

@@ -1,48 +0,0 @@
{ lib, platform }:
let
self = {
os =
if platform.isLinux then
"linux"
else if platform.isDarwin then
"macos"
else if platform.isWindows then
"windows"
else
throw "Unsupported OS \"${platform.parsed.kernel.name}\"";
alt-os = if platform.isDarwin then "mac" else self.os;
arch =
if platform.isx86_64 then
"amd64"
else if platform.isx86 && platform.is32bit then
"386"
else if platform.isAarch64 then
"arm64"
else if platform.isMips && platform.parsed.cpu.significantByte == "littleEndian" then
"mipsle"
else if platform.isMips64 then
"mips64${lib.optionalString (platform.parsed.cpu.significantByte == "littleEndian") "le"}"
else if platform.isPower64 then
"ppc64${lib.optionalString (platform.parsed.cpu.significantByte == "littleEndian") "le"}"
else if platform.isS390x then
"s390x"
else if platform.isRiscV64 then
"riscv64"
else
throw "Unsupported CPU \"${platform.parsed.cpu.name}\"";
alt-arch =
if platform.isx86_64 then
"x64"
else if platform.isAarch64 then
"arm64"
else
platform.parsed.cpu.name;
platform = "${self.os}-${self.arch}";
alt-platform = "${self.os}-${self.alt-arch}";
};
in
self

View File

@@ -1,12 +0,0 @@
{ engine, runCommand }:
runCommand "flutter-engine-${engine.version}-dart"
{
version = engine.dartSdkVersion;
meta = engine.meta // {
description = "Dart SDK compiled from the Flutter Engine";
};
}
''
ln --symbolic ${engine}/out/${engine.outName}/dart-sdk $out
''

View File

@@ -1,81 +0,0 @@
{
callPackage,
dartSdkVersion,
flutterVersion,
swiftshaderHash,
swiftshaderRev,
version,
hashes,
url,
patches,
runtimeModes,
lib,
stdenv,
...
}@args:
let
mainRuntimeMode = args.mainRuntimeMode or builtins.elemAt runtimeModes 0;
altRuntimeMode = args.altRuntimeMode or builtins.elemAt runtimeModes 1;
runtimeModesBuilds = lib.genAttrs runtimeModes (
runtimeMode:
callPackage ./package.nix {
inherit
dartSdkVersion
flutterVersion
swiftshaderHash
swiftshaderRev
version
hashes
url
patches
runtimeMode
;
isOptimized = args.isOptimized or runtimeMode != "debug";
}
);
in
stdenv.mkDerivation (
{
pname = "flutter-engine";
inherit url runtimeModes altRuntimeMode;
inherit (runtimeModesBuilds.${mainRuntimeMode}) version src meta;
strictDeps = true;
__structuredAttrs = true;
dontUnpack = true;
dontBuild = true;
installPhase = ''
runHook preInstall
mkdir --parents $out/out
''
+ lib.concatMapStrings (
runtimeMode:
let
runtimeModeBuild = runtimeModesBuilds.${runtimeMode};
runtimeModeOut = runtimeModeBuild.outName;
in
''
ln --symbolic --force ${runtimeModeBuild}/out/${runtimeModeOut} $out/out/${runtimeModeOut}
''
) runtimeModes
+ ''
runHook postInstall
'';
passthru = {
inherit (runtimeModesBuilds.${mainRuntimeMode})
dartSdkVersion
isOptimized
runtimeMode
outName
dart
swiftshader
;
};
}
// runtimeModesBuilds
)

View File

@@ -1,389 +0,0 @@
{
lib,
callPackage,
fetchurl,
bash,
symlinkJoin,
darwin,
clang,
tools ? callPackage ./tools.nix {
inherit (stdenv)
hostPlatform
buildPlatform
;
},
stdenv,
dart,
fetchgit,
llvmPackages,
patchelf,
gn,
openbox,
xorg-server,
libxxf86vm,
libxrender,
libxrandr,
libxi,
libxinerama,
libxfixes,
libxext,
libxcursor,
libx11,
xorgproto,
libxcb,
libglvnd,
libepoxy,
wayland,
freetype,
pango,
glib,
harfbuzz,
cairo,
gdk-pixbuf,
at-spi2-atk,
zlib,
gtk3,
pkg-config,
ninja,
python312,
gitMinimal,
version,
flutterVersion,
dartSdkVersion,
swiftshaderHash,
swiftshaderRev,
hashes,
patches,
url,
runtimeMode ? "release",
isOptimized ? runtimeMode != "debug",
}:
let
constants = callPackage ./constants.nix { platform = stdenv.targetPlatform; };
python3 = python312;
src = callPackage ./source.nix {
inherit
flutterVersion
version
hashes
url
;
inherit (stdenv)
hostPlatform
buildPlatform
targetPlatform
;
};
swiftshader = fetchgit {
url = "https://swiftshader.googlesource.com/SwiftShader.git";
hash = swiftshaderHash;
rev = swiftshaderRev;
postFetch = ''
rm --recursive --force $out/third_party/llvm-project
'';
};
llvm = symlinkJoin {
name = "llvm";
paths = [
clang
llvmPackages.llvm
];
};
outName = "host_${runtimeMode}${lib.optionalString (!isOptimized) "_unopt"}";
dartPath = "flutter/third_party/dart";
in
stdenv.mkDerivation (finalAttrs: {
pname = "flutter-engine-${runtimeMode}${lib.optionalString (!isOptimized) "-unopt"}";
inherit version src patches;
setOutputFlags = false;
doStrip = isOptimized;
toolchain = symlinkJoin {
name = "flutter-engine-toolchain-${version}";
paths =
lib.flatten (
map (dep: lib.optionals (lib.isDerivation dep) ([ dep ] ++ map (output: dep.${output}) dep.outputs))
(
lib.optionals (stdenv.hostPlatform.isLinux) [
gtk3
wayland
libepoxy
libglvnd
freetype
at-spi2-atk
glib
gdk-pixbuf
harfbuzz
pango
cairo
libxcb
libx11
libxcursor
libxrandr
libxrender
libxinerama
libxi
libxext
libxfixes
libxxf86vm
xorgproto
zlib
]
++ lib.optionals (stdenv.hostPlatform.isDarwin) [
clang
llvm
]
)
)
++ [
stdenv.cc.libc_dev
stdenv.cc.libc_lib
];
# Needed due to Flutter expecting everything to be relative to $out
# and not true absolute path (ie relative to "/").
postBuild = ''
mkdir --parents $(dirname $(dirname "$out/$out"))
ln --symbolic $(dirname "$out") $out/$(dirname "$out")
'';
};
NIX_CFLAGS_COMPILE = [
"-I${finalAttrs.toolchain}/include"
"-O2"
"-Wno-error"
"-Wno-absolute-value"
"-Wno-implicit-float-conversion"
]
++ lib.optional (!isOptimized) "-U_FORTIFY_SOURCE";
nativeCheckInputs = lib.optionals stdenv.hostPlatform.isLinux [
xorg-server
openbox
];
nativeBuildInputs = [
(python3.withPackages (
ps: with ps; [
pyyaml
]
))
(tools.vpython python3)
gitMinimal
pkg-config
ninja
dart
]
++ lib.optionals (stdenv.hostPlatform.isLinux) [ patchelf ]
++ lib.optionals (stdenv.hostPlatform.isDarwin) [
darwin.system_cmds
darwin.xcode
tools.xcode-select
]
++ lib.optionals (stdenv.cc.libc ? bin) [ stdenv.cc.libc.bin ];
buildInputs = [
gtk3
libepoxy
]
++ lib.optionals (lib.versionAtLeast flutterVersion "3.41") [
at-spi2-atk
glib
];
dontPatch = true;
env.patchgit = toString [
dartPath
"flutter"
"."
"flutter/third_party/skia"
];
postUnpack =
lib.optionalString (lib.versionAtLeast flutterVersion "3.38") ''
chmod +w .
mkdir --parents bin/internal
echo '#!${lib.getExe bash}' > bin/internal/content_aware_hash.sh
echo 'echo 1111111111111111111111111111111111111111' >> bin/internal/content_aware_hash.sh
chmod +x bin/internal/content_aware_hash.sh
''
+ ''
pushd ${finalAttrs.src.name}
cp ${
fetchurl {
url = "https://raw.githubusercontent.com/chromium/chromium/631a813125b886a52274653144019fd1681a0e97/build/config/linux/pkg-config.py";
hash = "sha256-9coRpgCewlkFXSGrMVkudaZUll0IFc9jDRBP+2PloOI=";
}
} src/build/config/linux/pkg-config.py
cp --preserve=mode,ownership,timestamps --recursive --reflink=auto ${swiftshader} src/flutter/third_party/swiftshader
chmod --recursive u+w -- src/flutter/third_party/swiftshader
ln --symbolic ${llvmPackages.llvm.monorepoSrc} src/flutter/third_party/swiftshader/third_party/llvm-project
mkdir --parents src/flutter/buildtools/${constants.alt-platform}
ln --symbolic ${llvm} src/flutter/buildtools/${constants.alt-platform}/clang
mkdir --parents src/buildtools/${constants.alt-platform}
ln --symbolic ${llvm} src/buildtools/${constants.alt-platform}/clang
mkdir --parents src/${dartPath}/tools/sdks
ln --symbolic ${dart} src/${dartPath}/tools/sdks/dart-sdk
mkdir --parents src/flutter/third_party/gn/
ln --symbolic --force ${lib.getExe gn} src/flutter/third_party/gn/gn
for dir in ''${patchgit[@]}; do
pushd src/$dir
rm --recursive --force .git
git init
git add .
git config user.name "nobody"
git config user.email "nobody@local.host"
git commit --all --message="$dir" --quiet
popd
done
dart src/${dartPath}/tools/generate_package_config.dart
echo "${dartSdkVersion}" >src/${dartPath}/sdk/version
python3 src/flutter/third_party/dart/tools/generate_sdk_version_file.py
rm --recursive --force src/third_party/angle/.git
python3 src/flutter/tools/pub_get_offline.py
pushd src/flutter
for p in ''${patches[@]}; do
patch -p1 -i $p
done
popd
''
# error: 'close_range' is missing exception specification 'noexcept(true)'
+ lib.optionalString (lib.versionAtLeast flutterVersion "3.35") ''
substituteInPlace src/flutter/third_party/dart/runtime/bin/process_linux.cc \
--replace-fail "(unsigned int first, unsigned int last, int flags)" "(unsigned int first, unsigned int last, int flags) noexcept(true)"
''
# src/flutter/third_party/libcxx/include/__type_traits/is_referenceable.h:33:1: error: templates must have C++ linkage
+ lib.optionalString (lib.versionAtLeast flutterVersion "3.41") ''
substituteInPlace src/flutter/shell/platform/linux/fl_view_accessible.cc \
--replace-fail "// Workaround missing C code compatibility in ATK header." "#include <glib.h>"
''
+ ''
popd
'';
configureFlags = [
"--no-prebuilt-dart-sdk"
"--embedder-for-target"
"--no-goma"
"--no-dart-version-git-info"
]
++ lib.optionals (stdenv.targetPlatform.isx86_64 == false) [
"--linux"
"--linux-cpu ${constants.alt-arch}"
]
++ lib.optional (!isOptimized) "--unoptimized"
++ lib.optional (runtimeMode == "debug") "--no-stripped"
++ lib.optional finalAttrs.finalPackage.doCheck "--enable-unittests"
++ lib.optional (!finalAttrs.finalPackage.doCheck) "--no-enable-unittests";
configurePhase = ''
runHook preConfigure
export PYTHONPATH=$src/src/build
''
+ lib.optionalString stdenv.hostPlatform.isDarwin ''
export PATH=${darwin.xcode}/Contents/Developer/usr/bin/:$PATH
''
+ ''
python3 ./src/flutter/tools/gn $configureFlags \
--runtime-mode ${runtimeMode} \
--out-dir $out \
--target-sysroot ${finalAttrs.toolchain} \
--target-dir ${outName} \
--target-triple ${stdenv.targetPlatform.config} \
--enable-fontconfig
runHook postConfigure
'';
buildPhase = ''
runHook preBuild
export TERM=dumb
''
# ValueError: ZIP does not support timestamps before 1980
+ ''
substituteInPlace src/flutter/build/zip.py \
--replace-fail "zipfile.ZipFile(args.output, 'w', zipfile.ZIP_DEFLATED)" "zipfile.ZipFile(args.output, 'w', zipfile.ZIP_DEFLATED, strict_timestamps=False)"
''
+ ''
ninja -C $out/out/${outName} -j$NIX_BUILD_CORES
runHook postBuild
'';
# Tests are broken
doCheck = false;
checkPhase = ''
runHook preCheck
ln --symbolic $out/out src/out
touch src/out/run_tests.log
sh src/flutter/testing/run_tests.sh ${outName}
rm src/out/run_tests.log
runHook postCheck
'';
installPhase = ''
runHook preInstall
rm --recursive --force $out/out/${outName}/{obj,exe.unstripped,lib.unstripped,zip_archives}
rm $out/out/${outName}/{args.gn,build.ninja,build.ninja.d,compile_commands.json,toolchain.ninja}
find $out/out/${outName} -name '*_unittests' -delete
find $out/out/${outName} -name '*_benchmarks' -delete
''
+ lib.optionalString (finalAttrs.finalPackage.doCheck) ''
rm $out/out/${outName}/{display_list_rendertests,flutter_tester}
''
+ ''
runHook postInstall
'';
passthru = {
inherit
dartSdkVersion
isOptimized
runtimeMode
outName
swiftshader
;
dart = callPackage ./dart.nix { engine = finalAttrs.finalPackage; };
};
meta = {
# Very broken on Darwin
broken = stdenv.hostPlatform.isDarwin;
description = "Flutter engine";
homepage = "https://flutter.dev";
maintainers = with lib.maintainers; [ RossComputerGuy ];
license = lib.licenses.bsd3;
platforms = [
"x86_64-linux"
"aarch64-linux"
"aarch64-darwin"
];
};
})

View File

@@ -1,103 +0,0 @@
{
lib,
callPackage,
curlMinimal,
pkg-config,
gitMinimal,
python312,
runCommand,
writeText,
cacert,
flutterVersion,
version,
hashes,
url,
hostPlatform,
targetPlatform,
buildPlatform,
...
}@pkgs:
let
target-constants = callPackage ./constants.nix { platform = targetPlatform; };
build-constants = callPackage ./constants.nix { platform = buildPlatform; };
tools = pkgs.tools or (callPackage ./tools.nix { inherit hostPlatform buildPlatform; });
boolOption = value: if value then "True" else "False";
gclient = writeText "flutter-${version}.gclient" ''
solutions = [{
"managed": False,
"name": ".",
"url": "${url}",
"custom_vars": {
"download_fuchsia_deps": False,
"download_android_deps": False,
"download_linux_deps": ${boolOption targetPlatform.isLinux},
"setup_githooks": False,
"download_esbuild": False,
"download_dart_sdk": True,
"host_cpu": "${build-constants.alt-arch}",
"host_os": "${build-constants.alt-os}",
},
}]
target_os_only = True
target_os = [
"${target-constants.alt-os}"
]
target_cpu_only = True
target_cpu = [
"${target-constants.alt-arch}"
]
'';
in
runCommand "flutter-engine-source-${version}-${buildPlatform.system}-${targetPlatform.system}"
{
pname = "flutter-engine-source";
inherit version;
nativeBuildInputs = [
curlMinimal
pkg-config
gitMinimal
tools.cipd
(python312.withPackages (
ps: with ps; [
httplib2
six
]
))
];
env = {
NIX_SSL_CERT_FILE = "${cacert}/etc/ssl/certs/ca-bundle.crt";
GIT_SSL_CAINFO = "${cacert}/etc/ssl/certs/ca-bundle.crt";
SSL_CERT_FILE = "${cacert}/etc/ssl/certs/ca-bundle.crt";
DEPOT_TOOLS_UPDATE = "0";
DEPOT_TOOLS_COLLECT_METRICS = "0";
PYTHONDONTWRITEBYTECODE = "1";
};
outputHashAlgo = "sha256";
outputHashMode = "recursive";
outputHash =
(hashes."${buildPlatform.system}" or { })."${targetPlatform.system}"
or (throw "Hash not set for ${targetPlatform.system} on ${buildPlatform.system}");
}
''
source ${../../../../build-support/fetchgit/deterministic-git}
export -f clean_git
export -f make_deterministic_repo
mkdir --parents flutter
cp ${gclient} flutter/.gclient
cd flutter
export PATH=$PATH:${tools.depot_tools}
python3 ${tools.depot_tools}/gclient.py sync --no-history --shallow --nohooks -j $NIX_BUILD_CORES
mv engine $out
find $out -name '.git' -exec rm --recursive --force {} \; || true
rm --recursive $out/src/flutter/{buildtools,prebuilts,third_party/swiftshader,third_party/gn/.versions,third_party/dart/tools/sdks/dart-sdk}
''

View File

@@ -2,7 +2,7 @@
stdenv,
buildPlatform,
hostPlatform,
callPackage,
lib,
fetchgit,
fetchurl,
writeText,
@@ -34,9 +34,66 @@
},
}:
let
constants = callPackage ./constants.nix { platform = buildPlatform; };
host-constants = callPackage ./constants.nix { platform = hostPlatform; };
stdenv-constants = callPackage ./constants.nix { platform = stdenv.hostPlatform; };
# Pure function computing the CIPD platform string for a given nixpkgs
# platform. Previously lived in ./constants.nix, which was removed together
# with the flutterPackages-source mechanism (#546540).
mkConstants =
platform:
let
os =
if platform.isLinux then
"linux"
else if platform.isDarwin then
"macos"
else if platform.isWindows then
"windows"
else
throw "Unsupported OS \"${platform.parsed.kernel.name}\"";
alt-os = if platform.isDarwin then "mac" else os;
arch =
if platform.isx86_64 then
"amd64"
else if platform.isx86 && platform.is32bit then
"386"
else if platform.isAarch64 then
"arm64"
else if platform.isMips && platform.parsed.cpu.significantByte == "littleEndian" then
"mipsle"
else if platform.isMips64 then
"mips64${lib.optionalString (platform.parsed.cpu.significantByte == "littleEndian") "le"}"
else if platform.isPower64 then
"ppc64${lib.optionalString (platform.parsed.cpu.significantByte == "littleEndian") "le"}"
else if platform.isS390x then
"s390x"
else if platform.isRiscV64 then
"riscv64"
else
throw "Unsupported CPU \"${platform.parsed.cpu.name}\"";
alt-arch =
if platform.isx86_64 then
"x64"
else if platform.isAarch64 then
"arm64"
else
platform.parsed.cpu.name;
in
{
inherit
os
alt-os
arch
alt-arch
;
platform = "${os}-${arch}";
alt-platform = "${os}-${alt-arch}";
};
constants = mkConstants buildPlatform;
host-constants = mkConstants hostPlatform;
stdenv-constants = mkConstants stdenv.hostPlatform;
in
{
depot_tools = fetchgit {

View File

@@ -1,16 +1,6 @@
{
useNixpkgsEngine ? false,
version,
engineVersion,
engineHashes ? { },
engineUrl ? "https://github.com/flutter/flutter.git@${engineVersion}",
enginePatches ? [ ],
engineRuntimeModes ? [
"release"
"debug"
],
engineSwiftShaderHash,
engineSwiftShaderRev,
patches,
channel,
dart,
@@ -31,24 +21,7 @@
}@args:
let
engine =
if args.useNixpkgsEngine or false then
callPackage ./engine/default.nix {
inherit (args) dart;
dartSdkVersion = args.dart.version;
flutterVersion = version;
swiftshaderRev = engineSwiftShaderRev;
swiftshaderHash = engineSwiftShaderHash;
version = engineVersion;
hashes = engineHashes;
url = engineUrl;
patches = enginePatches;
runtimeModes = engineRuntimeModes;
}
else
null;
dart = if args.useNixpkgsEngine or false then engine.dart else args.dart;
dart = args.dart;
flutterTools =
args.flutterTools or (callPackage ./flutter-tools.nix {
@@ -197,15 +170,9 @@ let
# When other derivations wrap this one, any unmodified files
# found here should be included as-is, for tooling compatibility.
sdk = unwrapped;
}
// lib.optionalAttrs (engine != null) {
inherit engine;
};
meta = {
# TODO: investigate why nixpkgs engine fails for versions >= 3.34
broken =
((lib.versionOlder version "3.32") || lib.versionAtLeast version "3.34") && useNixpkgsEngine;
description = "Makes it easy and fast to build beautiful apps for mobile and beyond";
longDescription = ''
Flutter is Google's SDK for crafting beautiful,
@@ -213,9 +180,7 @@ let
'';
homepage = "https://flutter.dev";
license = lib.licenses.bsd3;
sourceProvenance =
with lib.sourceTypes;
if useNixpkgsEngine then [ fromSource ] else [ binaryNativeCode ];
sourceProvenance = [ lib.sourceTypes.binaryNativeCode ];
platforms = [
"x86_64-linux"
"aarch64-linux"

View File

@@ -1,36 +0,0 @@
{
callPackage,
symlinkJoin,
lib,
}:
let
nixpkgsRoot = "@nixpkgs_root@";
version = "@flutter_version@";
engineVersion = "@engine_version@";
systemPlatforms = [
"x86_64-linux"
"aarch64-linux"
];
derivations = lib.foldl' (
acc: buildPlatform:
acc
++ (map (
targetPlatform:
callPackage "${nixpkgsRoot}/pkgs/development/compilers/flutter/engine/source.nix" {
targetPlatform = lib.systems.elaborate targetPlatform;
hostPlatform = lib.systems.elaborate buildPlatform;
buildPlatform = lib.systems.elaborate buildPlatform;
flutterVersion = version;
version = engineVersion;
url = "https://github.com/flutter/flutter.git@${engineVersion}";
hashes."${buildPlatform}"."${targetPlatform}" = "sha256-AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=";
}
) systemPlatforms)
) [ ] systemPlatforms;
in
symlinkJoin {
name = "evaluate-derivations";
paths = derivations;
}

View File

@@ -1,10 +0,0 @@
{ fetchgit }:
fetchgit {
url = "https://swiftshader.googlesource.com/SwiftShader.git";
rev = "@engine_swiftshader_rev@";
# Keep with in sync of pkgs/development/compilers/flutter/engine/package.nix
postFetch = ''
rm -rf $out/third_party/llvm-project
'';
}

View File

@@ -16,9 +16,8 @@ import yaml
FAKE_HASH = "sha256-AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA="
NIXPKGS_ROOT = (
subprocess.Popen(
["git", "rev-parse", "--show-toplevel"], stdout=subprocess.PIPE, text=True
)
subprocess
.Popen(["git", "rev-parse", "--show-toplevel"], stdout=subprocess.PIPE, text=True)
.communicate()[0]
.strip()
)
@@ -95,35 +94,6 @@ def nix_build_to_fail(code):
return stderr
def get_engine_hashes(engine_version, flutter_version):
code = load_code(
"get-engine-hashes.nix",
nixpkgs_root=NIXPKGS_ROOT,
flutter_version=flutter_version,
engine_version=engine_version,
)
stderr = nix_build_to_fail(code)
pattern = re.compile(
rf"/nix/store/.*-flutter-engine-source-{engine_version}-(.+?-.+?)-(.+?-.+?).drv':\n\s+specified: .*\n\s+got:\s+(.+?)\n"
)
matches = pattern.findall(stderr)
result_dict = {}
for match in matches:
flutter_platform, architecture, got = match
result_dict.setdefault(flutter_platform, {})[architecture] = got
def sort_dict_recursive(d):
return {
k: sort_dict_recursive(v) if isinstance(v, dict) else v
for k, v in sorted(d.items())
}
return sort_dict_recursive(result_dict)
def get_artifact_hashes(flutter_compact_version):
code = load_code(
"get-artifact-hashes.nix",
@@ -210,37 +180,11 @@ def get_pubspec_lock(flutter_compact_version, flutter_src):
return yaml.safe_load(pubspec_lock_yaml)
def get_engine_swiftshader_rev(engine_version):
with urllib.request.urlopen(
f"https://github.com/flutter/flutter/raw/{engine_version}/DEPS"
) as f:
deps = f.read().decode("utf-8")
pattern = re.compile(
r"Var\('swiftshader_git'\) \+ '\/SwiftShader\.git' \+ '@' \+ \'([0-9a-fA-F]{40})\'\,"
)
return pattern.findall(deps)[0]
def get_engine_swiftshader_hash(engine_swiftshader_rev):
code = load_code(
"get-engine-swiftshader.nix",
engine_swiftshader_rev=engine_swiftshader_rev,
hash="",
)
stderr = nix_build_to_fail(code)
pattern = re.compile(r"got:\s+(.+?)\n")
return pattern.findall(stderr)[0]
def write_data(
nixpkgs_flutter_version_directory,
flutter_version,
channel,
engine_hash,
engine_hashes,
engine_swiftshader_hash,
engine_swiftshader_rev,
dart_version,
dart_hash,
flutter_hash,
@@ -255,10 +199,7 @@ def write_data(
{
"version": flutter_version,
"engineVersion": engine_hash,
"engineSwiftShaderHash": engine_swiftshader_hash,
"engineSwiftShaderRev": engine_swiftshader_rev,
"channel": channel,
"engineHashes": engine_hashes,
"dartVersion": dart_version,
"dartHash": dart_hash,
"flutterHash": flutter_hash,
@@ -282,9 +223,6 @@ def update_all_packages():
new_content = [
"flutterPackages-bin = recurseIntoAttrs (callPackage ../development/compilers/flutter { });",
"flutterPackages-source = recurseIntoAttrs (",
" callPackage ../development/compilers/flutter { useNixpkgsEngine = true; }",
");",
"flutterPackages = flutterPackages-bin;",
"flutter = flutterPackages.stable;",
] + [
@@ -319,7 +257,7 @@ def update_all_packages():
file.write("".join(lines))
# Finds Flutter version, Dart version, and Engine hash.
# Finds Flutter version, and Dart version.
# If the Flutter version is given, it uses that. Otherwise finds the
# latest stable Flutter version.
def find_versions(flutter_version=None, channel=None):
@@ -345,7 +283,8 @@ def find_versions(flutter_version=None, channel=None):
flutter_version = release["version"]
tags = (
subprocess.Popen(
subprocess
.Popen(
["git", "ls-remote", "--tags", "https://github.com/flutter/flutter.git"],
stdout=subprocess.PIPE,
text=True,
@@ -445,9 +384,6 @@ def main():
write_data(
pubspec_lock={},
artifact_hashes={},
engine_hashes={},
engine_swiftshader_hash=FAKE_HASH,
engine_swiftshader_rev="0",
**common_data_args,
)
@@ -456,9 +392,6 @@ def main():
write_data(
pubspec_lock=pubspec_lock,
artifact_hashes={},
engine_hashes={},
engine_swiftshader_hash=FAKE_HASH,
engine_swiftshader_rev="0",
**common_data_args,
)
@@ -467,32 +400,18 @@ def main():
write_data(
pubspec_lock=pubspec_lock,
artifact_hashes=artifact_hashes,
engine_hashes={},
engine_swiftshader_hash=FAKE_HASH,
engine_swiftshader_rev="0",
**common_data_args,
)
engine_hashes = get_engine_hashes(engine_hash, flutter_version)
write_data(
pubspec_lock=pubspec_lock,
artifact_hashes=artifact_hashes,
engine_hashes=engine_hashes,
engine_swiftshader_hash=FAKE_HASH,
engine_swiftshader_rev="0",
**common_data_args,
)
engine_swiftshader_rev = get_engine_swiftshader_rev(engine_hash)
engine_swiftshader_hash = get_engine_swiftshader_hash(engine_swiftshader_rev)
write_data(
pubspec_lock=pubspec_lock,
artifact_hashes=artifact_hashes,
engine_hashes=engine_hashes,
engine_swiftshader_hash=engine_swiftshader_hash,
engine_swiftshader_rev=engine_swiftshader_rev,
**common_data_args,
)

View File

@@ -1,19 +1,7 @@
{
"version": "3.29.3",
"engineVersion": "cf56914b326edb0ccb123ffdc60f00060bd513fa",
"engineSwiftShaderHash": "sha256-mRLCvhNkmHz7Rv6GzXkY7OB1opBSq+ATWZ466qZdgto=",
"engineSwiftShaderRev": "2fa7e9b99ae4e70ea5ae2cc9c8d3afb43391384f",
"channel": "stable",
"engineHashes": {
"aarch64-linux": {
"aarch64-linux": "sha256-3BIBG9z433CDsBqX1T6K2y5kUI5ZTqXBBXLoCrX/f2A=",
"x86_64-linux": "sha256-3BIBG9z433CDsBqX1T6K2y5kUI5ZTqXBBXLoCrX/f2A="
},
"x86_64-linux": {
"aarch64-linux": "sha256-+4CswkW7+0gBcZKrLjugTIG5NWAxCB8y39iUxdND2I4=",
"x86_64-linux": "sha256-+4CswkW7+0gBcZKrLjugTIG5NWAxCB8y39iUxdND2I4="
}
},
"dartVersion": "3.7.2",
"dartHash": {
"x86_64-linux": "sha256-ClgSWEu0+lLcPIlabVvBY197/c/kyio6Zoq3KppbW3Y=",

View File

@@ -1,19 +1,7 @@
{
"version": "3.32.8",
"engineVersion": "ef0cd000916d64fa0c5d09cc809fa7ad244a5767",
"engineSwiftShaderHash": "sha256-ATVcuxqPHqHOWYyO7DoX9LdgUiO3INUi7m9Mc6ccc1M=",
"engineSwiftShaderRev": "d040a5bab638bf7c226235c95787ba6288bb6416",
"channel": "stable",
"engineHashes": {
"aarch64-linux": {
"aarch64-linux": "sha256-JrbIMYwdfe36y6bHj1eAjYOKPGGp7mfWxWDCoCm7wiQ=",
"x86_64-linux": "sha256-JrbIMYwdfe36y6bHj1eAjYOKPGGp7mfWxWDCoCm7wiQ="
},
"x86_64-linux": {
"aarch64-linux": "sha256-R0ut5hzzBgfjbZFB1ofK4jEmr3CcBKHFJUl3c7nmn0E=",
"x86_64-linux": "sha256-R0ut5hzzBgfjbZFB1ofK4jEmr3CcBKHFJUl3c7nmn0E="
}
},
"dartVersion": "3.8.1",
"dartHash": {
"x86_64-linux": "sha256-3eE40VMwrPFD502lIaz+CkD7mBnSI/WqJ3C4DVQ01Z4=",

View File

@@ -1,19 +1,7 @@
{
"version": "3.35.7",
"engineVersion": "035316565ad77281a75305515e4682e6c4c6f7ca",
"engineSwiftShaderHash": "sha256-ATVcuxqPHqHOWYyO7DoX9LdgUiO3INUi7m9Mc6ccc1M=",
"engineSwiftShaderRev": "d040a5bab638bf7c226235c95787ba6288bb6416",
"channel": "stable",
"engineHashes": {
"aarch64-linux": {
"aarch64-linux": "sha256-v2L0MQRTXvWngb8fu/AR9iofq2CDq1HFedXE8cSzOws=",
"x86_64-linux": "sha256-v2L0MQRTXvWngb8fu/AR9iofq2CDq1HFedXE8cSzOws="
},
"x86_64-linux": {
"aarch64-linux": "sha256-RKfKhFwlwVEguWqI6OinTqdCM3yNTP/5PwevREmS4Nk=",
"x86_64-linux": "sha256-RKfKhFwlwVEguWqI6OinTqdCM3yNTP/5PwevREmS4Nk="
}
},
"dartVersion": "3.9.2",
"dartHash": {
"x86_64-linux": "sha256-ZJcii2WBCE4PNt5+S2nH4hj+WoZuhRLFkzMlSZEa01Y=",

View File

@@ -1,19 +1,7 @@
{
"version": "3.38.10",
"engineVersion": "cafcda5721a78a7884db92f13c5e89f7643d52dd",
"engineSwiftShaderHash": "sha256-ATVcuxqPHqHOWYyO7DoX9LdgUiO3INUi7m9Mc6ccc1M=",
"engineSwiftShaderRev": "d040a5bab638bf7c226235c95787ba6288bb6416",
"channel": "stable",
"engineHashes": {
"aarch64-linux": {
"aarch64-linux": "sha256-qhOj6VT1aKhBApEr5R10NwalozUPMQKuUXfhcscTDTs=",
"x86_64-linux": "sha256-qhOj6VT1aKhBApEr5R10NwalozUPMQKuUXfhcscTDTs="
},
"x86_64-linux": {
"aarch64-linux": "sha256-VriQI7YmeM/HrZvLPRllxn5D/0r5xJiCzsn4XeBXO+A=",
"x86_64-linux": "sha256-VriQI7YmeM/HrZvLPRllxn5D/0r5xJiCzsn4XeBXO+A="
}
},
"dartVersion": "3.10.9",
"dartHash": {
"x86_64-linux": "sha256-Js8cesRAseVfa5CCQSmnJJVBYl+S7Zy7ax/vNbWMjQ0=",

View File

@@ -1,19 +1,7 @@
{
"version": "3.41.9",
"engineVersion": "42d3d75a56efe1a2e9902f52dc8006099c45d937",
"engineSwiftShaderHash": "sha256-qbtCl2nTpmtp9dnaoXc7rF3RqLnAZEmzw1BzPoCRWrc=",
"engineSwiftShaderRev": "794b0cfce1d828d187637e6d932bae484fbe0976",
"channel": "stable",
"engineHashes": {
"aarch64-linux": {
"aarch64-linux": "sha256-2nXNMgSXP2bwYUrHxofN1uu8ZnIPSVewR7Lg50BIW0E=",
"x86_64-linux": "sha256-2nXNMgSXP2bwYUrHxofN1uu8ZnIPSVewR7Lg50BIW0E="
},
"x86_64-linux": {
"aarch64-linux": "sha256-Tu0gC4wxbV8sGU46bODhQETlVs3D8fI4ziuL26Gt8Fw=",
"x86_64-linux": "sha256-Tu0gC4wxbV8sGU46bODhQETlVs3D8fI4ziuL26Gt8Fw="
}
},
"dartVersion": "3.11.5",
"dartHash": {
"x86_64-linux": "sha256-V/OrWsJIgwYLH/ErzaxHLtdlY+xzZOiPim1B5PDbB18=",

View File

@@ -1,19 +1,7 @@
{
"version": "3.44.4",
"engineVersion": "a10d8ac38de835021c8d2f920dbf50a920ccc030",
"engineSwiftShaderHash": "sha256-qbtCl2nTpmtp9dnaoXc7rF3RqLnAZEmzw1BzPoCRWrc=",
"engineSwiftShaderRev": "794b0cfce1d828d187637e6d932bae484fbe0976",
"channel": "stable",
"engineHashes": {
"aarch64-linux": {
"aarch64-linux": "sha256-R9xvuvdeoHLX4K52S7lAQW8iA7DIuIMjjntk1RcMVR8=",
"x86_64-linux": "sha256-R9xvuvdeoHLX4K52S7lAQW8iA7DIuIMjjntk1RcMVR8="
},
"x86_64-linux": {
"aarch64-linux": "sha256-zEbGTWZbsRG91YgHsyDU3wbXCLM0nk5TdbOAyjq1uMM=",
"x86_64-linux": "sha256-zEbGTWZbsRG91YgHsyDU3wbXCLM0nk5TdbOAyjq1uMM="
}
},
"dartVersion": "3.12.2",
"dartHash": {
"x86_64-linux": "sha256-KOR7RM8HXzZ3EEbAaLsNF0IBz5x2CHRK7RzCMgQpnC0=",

View File

@@ -1,35 +1,41 @@
This patch introduces an intermediate Gradle build step to alter the behavior
of flutter_tools' Gradle project, specifically moving the creation of `build`
and `.gradle` directories from within the Nix Store to somewhere in `$HOME/.cache/flutter/nix-flutter-tools-gradle/$engineShortRev`.
This patch redirects flutter_tools' Gradle project to build in a writable
directory at `$HOME/.cache/flutter/nix-flutter-tools-gradle/$engineShortRev`,
instead of within the read-only Nix Store.
Without this patch, flutter_tools' Gradle project tries to generate `build` and `.gradle`
directories within the Nix Store. Resulting in read-only errors when trying to build a
Flutter Android app at runtime.
Flutter Android app at runtime. In Gradle 9+, even the project directory itself must be
writable.
This patch takes advantage of the fact settings.gradle takes priority over settings.gradle.kts to build the intermediate Gradle project
when a Flutter app runs `includeBuild("${settings.ext.flutterSdkPath}/packages/flutter_tools/gradle")`
This patch takes advantage of the fact settings.gradle takes priority over settings.gradle.kts.
When a Flutter app runs `includeBuild("${settings.ext.flutterSdkPath}/packages/flutter_tools/gradle")`,
Gradle evaluates the `settings.gradle` we add, which:
1. Creates symlinks to `build.gradle.kts` and `src/` in the writable cache directory
2. Sets `rootProject.projectDir` to the writable cache directory
3. Applies the original `settings.gradle.kts` for dependency resolution
4. Redirects `buildDirectory` to the cache
`rootProject.buildFileName = "/dev/null"` so that the intermediate project doesn't use `build.gradle.kts` that's in the same directory.
The intermediate project makes a `settings.gradle` file in `$HOME/.cache/flutter/nix-flutter-tools-gradle/<short engine rev>/` and `includeBuild`s it.
This Gradle project will build the actual `packages/flutter_tools/gradle` project by setting
`rootProject.projectDir = new File("$settingsDir")` and `apply from: new File("$settingsDir/settings.gradle.kts")`.
To move `build` to `$HOME/.cache/flutter/nix-flutter-tools-gradle/<short engine rev>/`, we need to set `buildDirectory`.
To move `.gradle` as well, the `--project-cache-dir` argument must be passed to the Gradle wrapper.
Changing the `GradleUtils.getExecutable` function signature is a delibarate choice, to ensure that no new unpatched usages slip in.
Changing the `GradleUtils.getExecutable` function signature is a deliberate choice, to ensure that no new unpatched usages slip in.
--- /dev/null
+++ b/packages/flutter_tools/gradle/settings.gradle
@@ -0,0 +1,19 @@
+rootProject.buildFileName = "/dev/null"
+
@@ -0,0 +1,22 @@
+def engineShortRev = (new File("$settingsDir/../../../bin/internal/engine.version")).text.take(10)
+def dir = new File("$System.env.HOME/.cache/flutter/nix-flutter-tools-gradle/$engineShortRev")
+dir.mkdirs()
+def file = new File(dir, "settings.gradle")
+
+file.text = """
+rootProject.projectDir = new File("$settingsDir")
+def buildScript = new File(dir, "build.gradle.kts")
+if (!buildScript.exists()) {
+ java.nio.file.Files.createSymbolicLink(buildScript.toPath(), new File("$settingsDir/build.gradle.kts").toPath())
+}
+def srcLink = new File(dir, "src")
+if (!srcLink.exists()) {
+ java.nio.file.Files.createSymbolicLink(srcLink.toPath(), new File("$settingsDir/src").toPath())
+}
+
+rootProject.projectDir = dir
+
+apply from: new File("$settingsDir/settings.gradle.kts")
+
+gradle.allprojects { project ->
@@ -37,9 +43,6 @@ Changing the `GradleUtils.getExecutable` function signature is a delibarate choi
+ project.layout.buildDirectory = new File("$dir/build")
+ }
+}
+"""
+
+includeBuild(dir)
--- a/packages/flutter_tools/gradle/build.gradle.kts
+++ b/packages/flutter_tools/gradle/build.gradle.kts
@@ -4,6 +4,11 @@

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,21 @@
diff --git a/packages/flutter_tools/lib/src/flutter_cache.dart b/packages/flutter_tools/lib/src/flutter_cache.dart
index df67547..eacc7c4 100644
--- a/packages/flutter_tools/lib/src/flutter_cache.dart
+++ b/packages/flutter_tools/lib/src/flutter_cache.dart
@@ -51,16 +51,6 @@ class FlutterCache extends Cache {
registerArtifact(IosUsbArtifacts(artifactName, this, platform: platform));
}
registerArtifact(FontSubsetArtifacts(this, platform: platform));
- registerArtifact(
- PubDependencies(
- logger: logger,
- // flutter root and pub must be lazily initialized to avoid accessing
- // before the version is determined.
- flutterRoot: () => Cache.flutterRoot!,
- pub: () => pub,
- projectFactory: projectFactory,
- ),
- );
}
}

View File

@@ -0,0 +1,29 @@
diff --git a/packages/flutter_tools/lib/src/runner/flutter_command.dart b/packages/flutter_tools/lib/src/runner/flutter_command.dart
index e4e474ab6e..5548599802 100644
--- a/packages/flutter_tools/lib/src/runner/flutter_command.dart
+++ b/packages/flutter_tools/lib/src/runner/flutter_command.dart
@@ -1693,7 +1693,7 @@ Run 'flutter -h' (or 'flutter <command> -h') for available flutter commands and
// Populate the cache. We call this before pub get below so that the
// sky_engine package is available in the flutter cache for pub to find.
- if (shouldUpdateCache) {
+ if (false) {
// First always update universal artifacts, as some of these (e.g.
// ios-deploy on macOS) are required to determine `requiredArtifacts`.
final bool offline;
diff --git a/packages/flutter_tools/lib/src/runner/flutter_command_runner.dart b/packages/flutter_tools/lib/src/runner/flutter_command_runner.dart
index a1104da..1749d65 100644
--- a/packages/flutter_tools/lib/src/runner/flutter_command_runner.dart
+++ b/packages/flutter_tools/lib/src/runner/flutter_command_runner.dart
@@ -437,11 +437,6 @@
// Required to support `flutter --version` before artifacts are cached.
await globals.cache.updateAll(<DevelopmentArtifact>{DevelopmentArtifact.informative});
- globals.flutterVersion.ensureVersionFile();
- if (await _shouldCheckForUpdates(topLevelResults)) {
- await globals.flutterVersion.checkFlutterVersionFreshness();
- }
-
// See if the user specified a specific device.
final specifiedDeviceId = topLevelResults[FlutterGlobalOptions.kDeviceIdOption] as String?;
if (specifiedDeviceId != null) {

View File

@@ -0,0 +1,39 @@
Fix iOS build issue with NixOS/nixpkgs flutter
This patch cleans up xcode_backend.sh to use the FLUTTER_ROOT
environment variable directly, avoiding symlink traversal issues.
--- a/packages/flutter_tools/bin/xcode_backend.sh
+++ b/packages/flutter_tools/bin/xcode_backend.sh
@@ -10,27 +10,8 @@
#
# -------------------------------------------------------------------------- #
-# exit on error, or usage of unset var
-set -euo pipefail
+# Run `dart ./xcode_backend.dart` with the dart from $FLUTTER_ROOT.
+dart="${FLUTTER_ROOT}/bin/dart"
+xcode_backend_dart="${BASH_SOURCE[0]%.sh}.dart"
+exec "${dart}" "${xcode_backend_dart}" "$@" "ios"
-# Needed because if it is set, cd may print the path it changed to.
-unset CDPATH
-
-function follow_links() (
- cd -P -- "$(dirname -- "$1")"
- file="$PWD/$(basename -- "$1")"
- while [[ -h "$file" ]]; do
- cd -P -- "$(dirname -- "$file")"
- file="$(readlink -- "$file")"
- cd -P -- "$(dirname -- "$file")"
- file="$PWD/$(basename -- "$file")"
- done
- echo "$file"
-)
-
-PROG_NAME="$(follow_links "${BASH_SOURCE[0]}")"
-BIN_DIR="$(cd "${PROG_NAME%/*}" ; pwd -P)"
-FLUTTER_ROOT="$BIN_DIR/../../.."
-DART="$FLUTTER_ROOT/bin/dart"
-
-"$DART" "$BIN_DIR/xcode_backend.dart" "$@" "ios"

View File

@@ -0,0 +1,48 @@
Fix for macOS build issue in Flutter >= 3.35
Since version 3.35, the behavior of macos_assemble.sh and xcode_backend.sh
is almost identical. This caused the same error for macOS that previously
occurred for iOS.
Derived from the iOS patch: ./fix-ios-build-xcode-backend-sh.patch
--- a/packages/flutter_tools/bin/macos_assemble.sh
+++ b/packages/flutter_tools/bin/macos_assemble.sh
@@ -10,32 +10,13 @@
#
# -------------------------------------------------------------------------- #
-# exit on error, or usage of unset var
-set -euo pipefail
-
-# Needed because if it is set, cd may print the path it changed to.
-unset CDPATH
-
-function follow_links() (
- cd -P -- "$(dirname -- "$1")"
- file="$PWD/$(basename -- "$1")"
- while [[ -h "$file" ]]; do
- cd -P -- "$(dirname -- "$file")"
- file="$(readlink -- "$file")"
- cd -P -- "$(dirname -- "$file")"
- file="$PWD/$(basename -- "$file")"
- done
- echo "$file"
-)
-
-PROG_NAME="$(follow_links "${BASH_SOURCE[0]}")"
-BIN_DIR="$(cd "${PROG_NAME%/*}" ; pwd -P)"
-FLUTTER_ROOT="$BIN_DIR/../../.."
-DART="$FLUTTER_ROOT/bin/dart"
+# Run `dart ./xcode_backend.dart` with the dart from $FLUTTER_ROOT.
+dart="${FLUTTER_ROOT}/bin/dart"
+xcode_backend_dart="$(dirname "${BASH_SOURCE[0]}")/xcode_backend.dart"
# Main entry point.
if [[ $# == 0 ]]; then
- "$DART" "$BIN_DIR/xcode_backend.dart" "build" "macos"
+ exec "${dart}" "${xcode_backend_dart}" "build" "macos"
else
- "$DART" "$BIN_DIR/xcode_backend.dart" "$@" "macos"
+ exec "${dart}" "${xcode_backend_dart}" "$@" "macos"
fi

View File

@@ -0,0 +1,223 @@
This patch redirects flutter_tools' Gradle project to build in a writable
directory at `$HOME/.cache/flutter/nix-flutter-tools-gradle/$engineShortRev`,
instead of within the read-only Nix Store.
Without this patch, flutter_tools' Gradle project tries to generate `build` and `.gradle`
directories within the Nix Store. Resulting in read-only errors when trying to build a
Flutter Android app at runtime. In Gradle 9+, even the project directory itself must be
writable.
This patch takes advantage of the fact settings.gradle takes priority over settings.gradle.kts.
When a Flutter app runs `includeBuild("${settings.ext.flutterSdkPath}/packages/flutter_tools/gradle")`,
Gradle evaluates the `settings.gradle` we add, which:
1. Creates symlinks to `build.gradle.kts` and `src/` in the writable cache directory
2. Sets `rootProject.projectDir` to the writable cache directory
3. Applies the original `settings.gradle.kts` for dependency resolution
4. Redirects `buildDirectory` to the cache
To move `.gradle` as well, the `--project-cache-dir` argument must be passed to the Gradle wrapper.
Changing the `GradleUtils.getExecutable` function signature is a deliberate choice, to ensure that no new unpatched usages slip in.
--- /dev/null
+++ b/packages/flutter_tools/gradle/settings.gradle
@@ -0,0 +1,22 @@
+def engineShortRev = (new File("$settingsDir/../../../bin/internal/engine.version")).text.take(10)
+def dir = new File("$System.env.HOME/.cache/flutter/nix-flutter-tools-gradle/$engineShortRev")
+dir.mkdirs()
+
+def buildScript = new File(dir, "build.gradle.kts")
+if (!buildScript.exists()) {
+ java.nio.file.Files.createSymbolicLink(buildScript.toPath(), new File("$settingsDir/build.gradle.kts").toPath())
+}
+def srcLink = new File(dir, "src")
+if (!srcLink.exists()) {
+ java.nio.file.Files.createSymbolicLink(srcLink.toPath(), new File("$settingsDir/src").toPath())
+}
+
+rootProject.projectDir = dir
+
+apply from: new File("$settingsDir/settings.gradle.kts")
+
+gradle.allprojects { project ->
+ project.beforeEvaluate {
+ project.layout.buildDirectory = new File("$dir/build")
+ }
+}
--- a/packages/flutter_tools/gradle/build.gradle.kts
+++ b/packages/flutter_tools/gradle/build.gradle.kts
@@ -4,6 +4,11 @@
import org.jetbrains.kotlin.gradle.dsl.JvmTarget
+// While flutter_tools runs Gradle with a --project-cache-dir, this startParameter
+// is not passed correctly to the Kotlin Gradle plugin for some reason, and so
+// must be set here as well.
+gradle.startParameter.projectCacheDir = layout.buildDirectory.dir("cache").get().asFile
+
plugins {
`java-gradle-plugin`
groovy
--- a/packages/flutter_tools/lib/src/android/gradle.dart
+++ b/packages/flutter_tools/lib/src/android/gradle.dart
@@ -474,9 +474,9 @@ class AndroidGradleBuilder implements AndroidBuilder {
// from the local.properties file.
updateLocalProperties(project: project, buildInfo: androidBuildInfo.buildInfo);
- final options = <String>[];
-
- final String gradleExecutablePath = _gradleUtils.getExecutable(project);
+ final [String gradleExecutablePath, ...List<String> options] = _gradleUtils.getExecutable(
+ project,
+ );
// All automatically created files should exist.
if (configOnly) {
@@ -797,7 +797,7 @@ class AndroidGradleBuilder implements AndroidBuilder {
'aar_init_script.gradle',
);
final command = <String>[
- _gradleUtils.getExecutable(project),
+ ..._gradleUtils.getExecutable(project),
'-I=$initScript',
'-Pflutter-root=$flutterRoot',
'-Poutput-dir=${outputDirectory.path}',
@@ -912,6 +912,10 @@ class AndroidGradleBuilder implements AndroidBuilder {
final results = <String>[];
try {
+ final [String gradleExecutablePath, ...List<String> options] = _gradleUtils.getExecutable(
+ project,
+ );
+
exitCode = await _runGradleTask(
_kBuildVariantTaskName,
preRunTask: () {
@@ -927,10 +931,10 @@ class AndroidGradleBuilder implements AndroidBuilder {
),
);
},
- options: const <String>['-q'],
+ options: <String>[...options, '-q'],
project: project,
localGradleErrors: gradleErrors,
- gradleExecutablePath: _gradleUtils.getExecutable(project),
+ gradleExecutablePath: gradleExecutablePath,
outputParser: (String line) {
if (_kBuildVariantRegex.firstMatch(line) case final RegExpMatch match) {
results.add(match.namedGroup(_kBuildVariantRegexGroupName)!);
@@ -964,6 +968,10 @@ class AndroidGradleBuilder implements AndroidBuilder {
late Stopwatch sw;
var exitCode = 1;
try {
+ final [String gradleExecutablePath, ...List<String> options] = _gradleUtils.getExecutable(
+ project,
+ );
+
exitCode = await _runGradleTask(
taskName,
preRunTask: () {
@@ -979,10 +987,10 @@ class AndroidGradleBuilder implements AndroidBuilder {
),
);
},
- options: <String>['-q', '-PoutputPath=$outputPath'],
+ options: <String>[...options, '-q', '-PoutputPath=$outputPath'],
project: project,
localGradleErrors: gradleErrors,
- gradleExecutablePath: _gradleUtils.getExecutable(project),
+ gradleExecutablePath: gradleExecutablePath,
);
} on Error catch (error) {
_logger.printError(error.toString());
--- a/packages/flutter_tools/lib/src/android/gradle_errors.dart
+++ b/packages/flutter_tools/lib/src/android/gradle_errors.dart
@@ -228,7 +228,12 @@ final flavorUndefinedHandler = GradleHandledError(
},
handler: ({required String line, required FlutterProject project, required bool usesAndroidX}) async {
final RunResult tasksRunResult = await globals.processUtils.run(
- <String>[globals.gradleUtils!.getExecutable(project), 'app:tasks', '--all', '--console=auto'],
+ <String>[
+ ...globals.gradleUtils!.getExecutable(project),
+ 'app:tasks',
+ '--all',
+ '--console=auto',
+ ],
throwOnError: true,
workingDirectory: project.android.hostAppGradleRoot.path,
environment: globals.java?.environment,
--- a/packages/flutter_tools/lib/src/android/gradle_utils.dart
+++ b/packages/flutter_tools/lib/src/android/gradle_utils.dart
@@ -3,6 +3,7 @@
// found in the LICENSE file.
import 'package:meta/meta.dart';
+import 'package:path/path.dart';
import 'package:process/process.dart';
import 'package:unified_analytics/unified_analytics.dart';
@@ -197,9 +198,29 @@ class GradleUtils {
final Logger _logger;
final OperatingSystemUtils _operatingSystemUtils;
+ List<String> get _requiredArguments {
+ final String cacheDir = join(
+ switch (globals.platform.environment['XDG_CACHE_HOME']) {
+ final String cacheHome => cacheHome,
+ _ => join(
+ globals.fsUtils.homeDirPath ?? throwToolExit('No cache directory has been specified.'),
+ '.cache',
+ ),
+ },
+ 'flutter',
+ 'nix-flutter-tools-gradle',
+ globals.flutterVersion.engineRevision.substring(0, 10),
+ );
+
+ return <String>[
+ '--project-cache-dir=${join(cacheDir, 'cache')}',
+ '-Pkotlin.project.persistent.dir=${join(cacheDir, 'kotlin')}',
+ ];
+ }
+
/// Gets the Gradle executable path and prepares the Gradle project.
/// This is the `gradlew` or `gradlew.bat` script in the `android/` directory.
- String getExecutable(FlutterProject project) {
+ List<String> getExecutable(FlutterProject project) {
final Directory androidDir = project.android.hostAppGradleRoot;
injectGradleWrapperIfNeeded(androidDir);
@@ -210,7 +231,7 @@ class GradleUtils {
// If the Gradle executable doesn't have execute permission,
// then attempt to set it.
_operatingSystemUtils.makeExecutable(gradle);
- return gradle.absolute.path;
+ return <String>[gradle.absolute.path, ..._requiredArguments];
}
throwToolExit(
'Unable to locate gradlew script. Please check that ${gradle.path} '
--- a/packages/flutter_tools/test/general.shard/android/android_gradle_builder_test.dart
+++ b/packages/flutter_tools/test/general.shard/android/android_gradle_builder_test.dart
@@ -2606,8 +2606,8 @@ Gradle Crashed
class FakeGradleUtils extends Fake implements GradleUtils {
@override
- String getExecutable(FlutterProject project) {
- return 'gradlew';
+ List<String> getExecutable(FlutterProject project) {
+ return const <String>['gradlew'];
}
}
--- a/packages/flutter_tools/test/general.shard/android/gradle_errors_test.dart
+++ b/packages/flutter_tools/test/general.shard/android/gradle_errors_test.dart
@@ -1633,8 +1633,8 @@ Platform fakePlatform(String name) {
class FakeGradleUtils extends Fake implements GradleUtils {
@override
- String getExecutable(FlutterProject project) {
- return 'gradlew';
+ List<String> getExecutable(FlutterProject project) {
+ return const <String>['gradlew'];
}
}

View File

@@ -0,0 +1,22 @@
diff --git a/packages/flutter_tools/lib/src/base/os.dart b/packages/flutter_tools/lib/src/base/os.dart
index 45da89ad4c..0f7d9c2a11 100644
--- a/packages/flutter_tools/lib/src/base/os.dart
+++ b/packages/flutter_tools/lib/src/base/os.dart
@@ -147,7 +147,17 @@ abstract class OperatingSystemUtils {
/// Represents the platform of the host machine running the Flutter tool.
HostPlatform get hostPlatform {
+ const nixHostPlatform = String.fromEnvironment('NIX_FLUTTER_HOST_PLATFORM');
+ if (nixHostPlatform.isNotEmpty) {
+ return switch (nixHostPlatform) {
+ 'x86_64-linux' => HostPlatform.linux_x64,
+ 'aarch64-linux' => HostPlatform.linux_arm64,
+ 'x86_64-darwin' => HostPlatform.darwin_x64,
+ 'aarch64-darwin' => HostPlatform.darwin_arm64,
+ String value => throw ArgumentError.value(value, 'NIX_FLUTTER_HOST_PLATFORM', 'Unknown Nix host platform!'),
+ };
+ }
return switch (_currentAbi) {
Abi.macosX64 => HostPlatform.darwin_x64,
Abi.macosArm64 => HostPlatform.darwin_arm64,
};
}

View File

@@ -8,7 +8,7 @@
"universal"
"web"
]
++ lib.optional (stdenv.hostPlatform.isLinux && !(flutter ? engine)) "linux"
++ lib.optional stdenv.hostPlatform.isLinux "linux"
++ lib.optional (stdenv.hostPlatform.isx86_64 || stdenv.hostPlatform.isDarwin) "android"
++ lib.optionals stdenv.hostPlatform.isDarwin [
"macos"
@@ -190,12 +190,6 @@ in
mkdir --parents $out/bin
makeWrapper '${immutableFlutter}' $out/bin/flutter \
--set-default ANDROID_EMULATOR_USE_SYSTEM_LIBS 1 \
''
+ lib.optionalString (flutter ? engine && flutter.engine.meta.available) ''
--set-default FLUTTER_ENGINE "${flutter.engine}" \
--add-flags "--local-engine-host ${flutter.engine.outName}" \
''
+ ''
--suffix PATH : '${lib.makeBinPath (tools ++ buildTools)}' \
--suffix PKG_CONFIG_PATH : "$FLUTTER_PKG_CONFIG_PATH" \
--suffix LIBRARY_PATH : '${lib.makeLibraryPath appStaticBuildDeps}' \

View File

@@ -0,0 +1,38 @@
{
lib,
buildPythonPackage,
fetchFromGitHub,
setuptools,
unittestCheckHook,
unstableGitUpdater,
}:
buildPythonPackage (finalAttrs: {
pname = "bahttext";
version = "1.0.2-unstable-2020-05-31";
pyproject = true;
__structuredAttrs = true;
src = fetchFromGitHub {
owner = "sekz";
repo = "bahttext";
rev = "5dc3a6e9056a81cefb199c49ca69f9a7a9fa835b";
hash = "sha256-q/z64c5Nqq0PbUGBzyODQchTs2bV9ksujCMLB8ZCB/Y=";
};
build-system = [ setuptools ];
nativeCheckInputs = [ unittestCheckHook ];
pythonImportsCheck = [ "bahttext" ];
passthru.updateScript = unstableGitUpdater { };
meta = {
description = "Convert currency numbers to Thai Baht text";
homepage = "https://github.com/sekz/bahttext";
license = lib.licenses.bsd3;
maintainers = [ lib.maintainers.lucasew ];
teams = [ lib.teams.ngi ];
};
})

View File

@@ -11,10 +11,7 @@
# tests
pytestCheckHook,
beets-audible,
mediafile,
reflink,
toml,
typeguard,
writableTmpDirAsHomeHook,
}:
@@ -45,10 +42,6 @@ buildPythonPackage (finalAttrs: {
nativeCheckInputs = [
pytestCheckHook
beets-audible
mediafile
reflink
toml
typeguard
writableTmpDirAsHomeHook
];

View File

@@ -9,7 +9,7 @@
buildPythonPackage (finalAttrs: {
pname = "braintree";
version = "4.45.0";
version = "4.46.0";
pyproject = true;
__structuredAttrs = true;
@@ -18,7 +18,7 @@ buildPythonPackage (finalAttrs: {
owner = "braintree";
repo = "braintree_python";
tag = finalAttrs.version;
hash = "sha256-cD0TKqf2c/wdFwDc78rEPm4ucZkYS1nk2Uo0oTfcJvE=";
hash = "sha256-n2l0c62BhHKgxNko66aPZVKrzi2w5qXIrqBbJknkhkE=";
};
build-system = [ setuptools ];

Some files were not shown because too many files have changed in this diff Show More