···
1
-
{ callPackage, stdenv, stdenvNoCC, lib, fetchurl, ruby, writeText
2
-
, licenseAccepted ? false, meta
9
+
licenseAccepted ? false,
5
-
{ repoJson ? ./repo.json
8
-
# Reads the repo JSON. If repoXmls is provided, will build a repo JSON into the Nix store.
9
-
if repoXmls != null then
11
-
# Uses mkrepo.rb to create a repo spec.
12
-
mkRepoJson = { packages ? [], images ? [], addons ? [] }: let
13
-
mkRepoRuby = (ruby.withPackages (pkgs: with pkgs; [ slop nokogiri ]));
14
-
mkRepoRubyArguments = lib.lists.flatten [
15
-
(map (package: ["--packages" "${package}"]) packages)
16
-
(map (image: ["--images" "${image}"]) images)
17
-
(map (addon: ["--addons" "${addon}"]) addons)
14
+
repoJson ? ./repo.json,
17
+
# Reads the repo JSON. If repoXmls is provided, will build a repo JSON into the Nix store.
18
+
if repoXmls != null then
20
+
# Uses mkrepo.rb to create a repo spec.
36
+
mkRepoRubyArguments = lib.lists.flatten [
51
+
stdenvNoCC.mkDerivation {
52
+
name = "androidenv-repo-json";
53
+
buildInputs = [ mkRepoRuby ];
54
+
preferLocalBuild = true;
55
+
unpackPhase = "true";
57
+
ruby ${./mkrepo.rb} ${lib.escapeShellArgs mkRepoRubyArguments} > repo.json
64
+
packages = repoXmls.packages or [ ];
65
+
images = repoXmls.images or [ ];
66
+
addons = repoXmls.addons or [ ];
20
-
stdenvNoCC.mkDerivation {
21
-
name = "androidenv-repo-json";
22
-
buildInputs = [ mkRepoRuby ];
23
-
preferLocalBuild = true;
24
-
unpackPhase = "true";
26
-
ruby ${./mkrepo.rb} ${lib.escapeShellArgs mkRepoRubyArguments} > repo.json
33
-
packages = repoXmls.packages or [];
34
-
images = repoXmls.images or [];
35
-
addons = repoXmls.addons or [];
lib.importJSON "${mkRepoJson repoXmlSpec}"
40
-
lib.importJSON repoJson
42
-
, cmdLineToolsVersion ? repo.latest.cmdline-tools
43
-
, toolsVersion ? repo.latest.tools
44
-
, platformToolsVersion ? repo.latest.platform-tools
45
-
, buildToolsVersions ? [ repo.latest.build-tools ]
46
-
, includeEmulator ? false
47
-
, emulatorVersion ? repo.latest.emulator
48
-
, platformVersions ? [ repo.latest.platforms ]
49
-
, includeSources ? false
50
-
, includeSystemImages ? false
51
-
, systemImageTypes ? [ "google_apis" "google_apis_playstore" ]
52
-
, abiVersions ? [ "x86" "x86_64" "armeabi-v7a" "arm64-v8a" ]
71
+
lib.importJSON repoJson
73
+
cmdLineToolsVersion ? repo.latest.cmdline-tools,
74
+
toolsVersion ? repo.latest.tools,
75
+
platformToolsVersion ? repo.latest.platform-tools,
76
+
buildToolsVersions ? [ repo.latest.build-tools ],
77
+
includeEmulator ? false,
78
+
emulatorVersion ? repo.latest.emulator,
79
+
platformVersions ? [ repo.latest.platforms ],
80
+
includeSources ? false,
81
+
includeSystemImages ? false,
82
+
systemImageTypes ? [
84
+
"google_apis_playstore"
# cmake has precompiles on x86_64 and Darwin platforms. Default to true there for compatibility.
54
-
, includeCmake ? stdenv.hostPlatform.isx86_64 || stdenv.hostPlatform.isDarwin
55
-
, cmakeVersions ? [ repo.latest.cmake ]
56
-
, includeNDK ? false
57
-
, ndkVersion ? repo.latest.ndk
58
-
, ndkVersions ? [ ndkVersion ]
59
-
, useGoogleAPIs ? false
60
-
, useGoogleTVAddOns ? false
61
-
, includeExtras ? []
62
-
, extraLicenses ? []
93
+
includeCmake ? stdenv.hostPlatform.isx86_64 || stdenv.hostPlatform.isDarwin,
94
+
cmakeVersions ? [ repo.latest.cmake ],
96
+
ndkVersion ? repo.latest.ndk,
97
+
ndkVersions ? [ ndkVersion ],
98
+
useGoogleAPIs ? false,
99
+
useGoogleTVAddOns ? false,
100
+
includeExtras ? [ ],
101
+
extraLicenses ? [ ],
# Determine the Android os identifier from Nix's system identifier
x86_64-darwin = "macosx";
aarch64-darwin = "macosx";
72
-
}.${stdenv.hostPlatform.system} or "all";
113
+
.${stdenv.hostPlatform.system} or "all";
# Determine the Android arch identifier from Nix's system identifier
aarch64-linux = "aarch64";
aarch64-darwin = "aarch64";
80
-
}.${stdenv.hostPlatform.system} or "all";
123
+
.${stdenv.hostPlatform.system} or "all";
# Converts all 'archives' keys in a repo spec to fetchurl calls.
83
-
fetchArchives = attrSet:
84
-
lib.attrsets.mapAttrsRecursive
86
-
if (builtins.elemAt path (builtins.length path - 1)) == "archives" then
88
-
validArchives = builtins.filter (archive:
90
-
isTargetOs = if builtins.hasAttr "os" archive then
91
-
archive.os == os || archive.os == "all" else true;
92
-
isTargetArch = if builtins.hasAttr "arch" archive then
93
-
archive.arch == arch || archive.arch == "all" else true;
95
-
isTargetOs && isTargetArch
97
-
packageInfo = lib.attrByPath (lib.sublist 0 (builtins.length path - 1) path) null attrSet;
99
-
lib.optionals (builtins.length validArchives > 0)
100
-
(lib.last (map (archive:
128
+
lib.attrsets.mapAttrsRecursive (
130
+
if (builtins.elemAt path (builtins.length path - 1)) == "archives" then
132
+
validArchives = builtins.filter (
136
+
if builtins.hasAttr "os" archive then archive.os == os || archive.os == "all" else true;
138
+
if builtins.hasAttr "arch" archive then archive.arch == arch || archive.arch == "all" else true;
140
+
isTargetOs && isTargetArch
142
+
packageInfo = lib.attrByPath (lib.sublist 0 (builtins.length path - 1) path) null attrSet;
144
+
lib.optionals (builtins.length validArchives > 0) (
inherit (archive) url sha1;
# Converts the repo attrset into fetch calls.
···
# and add recurseIntoAttrs to all of them.
123
-
liftedArchives = lib.attrsets.mapAttrsRecursiveCond
124
-
(value: !(builtins.hasAttr "archives" value))
126
-
if (value.archives or null) != null && (value.archives or [ ]) != [ ] then
127
-
lib.dontRecurseIntoAttrs value.archives
173
+
liftedArchives = lib.attrsets.mapAttrsRecursiveCond (value: !(builtins.hasAttr "archives" value)) (
175
+
if (value.archives or null) != null && (value.archives or [ ]) != [ ] then
176
+
lib.dontRecurseIntoAttrs value.archives
# Creates a version key from a name.
# Converts things like 'extras;google;auto' to 'extras-google-auto'
134
-
toVersionKey = name:
lib.optionalString (lib.match "^[0-9].*" name != null) "v"
136
-
+ lib.concatStringsSep "_" (lib.splitVersion (lib.replaceStrings [ ";" ] [ "-" ] name));
186
+
+ lib.concatStringsSep "_" (lib.splitVersion (lib.replaceStrings [ ";" ] [ "-" ] name));
138
-
recurse = lib.mapAttrs'
140
-
if builtins.isAttrs value && (value.recurseForDerivations or true) then
141
-
lib.nameValuePair (toVersionKey name) (lib.recurseIntoAttrs (recurse value))
143
-
lib.nameValuePair (toVersionKey name) value
188
+
recurse = lib.mapAttrs' (
190
+
if builtins.isAttrs value && (value.recurseForDerivations or true) then
191
+
lib.nameValuePair (toVersionKey name) (lib.recurseIntoAttrs (recurse value))
193
+
lib.nameValuePair (toVersionKey name) value
lib.recurseIntoAttrs (recurse liftedArchives);
···
# Converts a list of license names to a flattened list of license texts.
# Just used for displaying licenses.
153
-
mkLicenseTexts = licenseNames:
158
-
(licenseText: "--- ${licenseName} ---\n${licenseText}")
159
-
(mkLicenses licenseName))
205
+
lib.lists.flatten (
208
+
builtins.map (licenseText: "--- ${licenseName} ---\n${licenseText}") (mkLicenses licenseName)
# Converts a license name to a list of license hashes.
163
-
mkLicenseHashes = licenseName:
165
-
(licenseText: builtins.hashString "sha1" licenseText)
166
-
(mkLicenses licenseName);
215
+
builtins.map (licenseText: builtins.hashString "sha1" licenseText) (mkLicenses licenseName);
# The list of all license names we're accepting. Put android-sdk-license there
170
-
licenseNames = lib.lists.unique ([
171
-
"android-sdk-license"
172
-
] ++ extraLicenses);
219
+
licenseNames = lib.lists.unique (
221
+
"android-sdk-license"
# put a much nicer error message that includes the available options.
175
-
check-version = packages: package: version:
228
+
packages: package: version:
if lib.hasAttrByPath [ package version ] packages then
packages.${package}.${version}
The version ${version} is missing in package ${package}.
181
-
The only available versions are ${builtins.concatStringsSep ", " (builtins.attrNames packages.${package})}.
234
+
The only available versions are ${
235
+
builtins.concatStringsSep ", " (builtins.attrNames packages.${package})
# Returns true if we should link the specified plugins.
185
-
shouldLink = check: packages:
assert builtins.isList packages;
···
else if check == null || check == "if-supported" then
193
-
hasSrc = package: package.src != null && (builtins.isList package.src -> builtins.length package.src > 0);
250
+
package: package.src != null && (builtins.isList package.src -> builtins.length package.src > 0);
195
-
packages != [] && lib.all hasSrc packages
252
+
packages != [ ] && lib.all hasSrc packages
throw "Invalid argument ${toString check}; use true, false, or null/if-supported";
# Function that automatically links all plugins for which multiple versions can coexist
200
-
linkPlugins = {name, plugins, check ? true}:
lib.optionalString (shouldLink check plugins) ''
${lib.concatMapStrings (plugin: ''
···
# Function that automatically links all NDK plugins.
209
-
linkNdkPlugins = {name, plugins, rootName ? name, check ? true}:
lib.optionalString (shouldLink check plugins) ''
${lib.concatMapStrings (plugin: ''
···
# Function that automatically links the default NDK plugin.
218
-
linkNdkPlugin = {name, plugin, check}:
219
-
lib.optionalString (shouldLink check [plugin]) ''
292
+
lib.optionalString (shouldLink check [ plugin ]) ''
ln -s ${plugin}/libexec/android-sdk/${name} ${name}
# Function that automatically links a plugin for which only one version exists
224
-
linkPlugin = {name, plugin, check ? true}:
225
-
lib.optionalString (shouldLink check [plugin]) ''
303
+
lib.optionalString (shouldLink check [ plugin ]) ''
ln -s ${plugin}/libexec/android-sdk/${name} ${name}
229
-
linkSystemImages = { images, check }: lib.optionalString (shouldLink check images) ''
230
-
mkdir -p system-images
231
-
${lib.concatMapStrings (system-image: ''
232
-
apiVersion=$(basename $(echo ${system-image}/libexec/android-sdk/system-images/*))
233
-
type=$(basename $(echo ${system-image}/libexec/android-sdk/system-images/*/*))
234
-
mkdir -p system-images/$apiVersion
235
-
ln -s ${system-image}/libexec/android-sdk/system-images/$apiVersion/$type system-images/$apiVersion/$type
309
+
lib.optionalString (shouldLink check images) ''
310
+
mkdir -p system-images
311
+
${lib.concatMapStrings (system-image: ''
312
+
apiVersion=$(basename $(echo ${system-image}/libexec/android-sdk/system-images/*))
313
+
type=$(basename $(echo ${system-image}/libexec/android-sdk/system-images/*/*))
314
+
mkdir -p system-images/$apiVersion
315
+
ln -s ${system-image}/libexec/android-sdk/system-images/$apiVersion/$type system-images/$apiVersion/$type
# Links all plugins related to a requested platform
240
-
linkPlatformPlugins = {name, plugins, check}:
320
+
linkPlatformPlugins =
lib.optionalString (shouldLink check plugins) ''
${lib.concatMapStrings (plugin: ''
···
lib.recurseIntoAttrs rec {
deployAndroidPackages = callPackage ./deploy-androidpackages.nix {
251
-
inherit stdenv lib mkLicenses meta os arch;
254
-
deployAndroidPackage = ({package, buildInputs ? [], patchInstructions ? "", meta ? {}, ...}@args:
346
+
deployAndroidPackage = (
350
+
patchInstructions ? "",
256
-
extraParams = removeAttrs args [ "package" "os" "arch" "buildInputs" "patchInstructions" ];
355
+
extraParams = removeAttrs args [
360
+
"patchInstructions"
258
-
deployAndroidPackages ({
259
-
inherit buildInputs;
260
-
packages = [ package ];
261
-
patchesInstructions = { "${package.name}" = patchInstructions; };
363
+
deployAndroidPackages (
365
+
inherit buildInputs;
366
+
packages = [ package ];
367
+
patchesInstructions = {
368
+
"${package.name}" = patchInstructions;
platform-tools = callPackage ./platform-tools.nix {
268
-
inherit deployAndroidPackage os arch meta;
379
+
deployAndroidPackage
package = check-version allArchives.packages "platform-tools" platformToolsVersion;
tools = callPackage ./tools.nix {
273
-
inherit deployAndroidPackage os arch meta;
389
+
deployAndroidPackage
package = check-version allArchives.packages "tools" toolsVersion;
277
-
${linkPlugin { name = "platform-tools"; plugin = platform-tools; }}
278
-
${linkPlugin { name = "emulator"; plugin = emulator; check = includeEmulator; }}
398
+
name = "platform-tools";
399
+
plugin = platform-tools;
404
+
check = includeEmulator;
282
-
build-tools = map (version:
409
+
build-tools = map (
callPackage ./build-tools.nix {
284
-
inherit deployAndroidPackage os arch meta;
413
+
deployAndroidPackage
package = check-version allArchives.packages "build-tools" version;
288
-
${linkPlugin { name = "tools"; plugin = tools; check = toolsVersion != null; }}
424
+
check = toolsVersion != null;
294
-
callPackage ./emulator.nix {
295
-
inherit deployAndroidPackage os arch meta;
296
-
package = check-version allArchives.packages "emulator" emulatorVersion;
430
+
emulator = callPackage ./emulator.nix {
432
+
deployAndroidPackage
437
+
package = check-version allArchives.packages "emulator" emulatorVersion;
299
-
${linkSystemImages { images = system-images; check = includeSystemImages; }}
440
+
${linkSystemImages {
441
+
images = system-images;
442
+
check = includeSystemImages;
303
-
platforms = map (version:
package = check-version allArchives.packages "platforms" version;
309
-
sources = map (version:
package = check-version allArchives.packages "sources" version;
315
-
system-images = lib.flatten (map (apiVersion:
317
-
# Deploy all system images with the same systemImageType in one derivation to avoid the `null` problem below
318
-
# with avdmanager when trying to create an avd!
321
-
# $ yes "" | avdmanager create avd --force --name testAVD --package 'system-images;android-33;google_apis;x86_64'
322
-
# Error: Package path is not valid. Valid system image paths are:
326
-
availablePackages = map (abiVersion:
327
-
allArchives.system-images.${apiVersion}.${type}.${abiVersion}
328
-
) (builtins.filter (abiVersion:
329
-
lib.hasAttrByPath [apiVersion type abiVersion] allArchives.system-images
461
+
system-images = lib.flatten (
466
+
# Deploy all system images with the same systemImageType in one derivation to avoid the `null` problem below
467
+
# with avdmanager when trying to create an avd!
470
+
# $ yes "" | avdmanager create avd --force --name testAVD --package 'system-images;android-33;google_apis;x86_64'
471
+
# Error: Package path is not valid. Valid system image paths are:
475
+
availablePackages =
476
+
map (abiVersion: allArchives.system-images.${apiVersion}.${type}.${abiVersion})
479
+
abiVersion: lib.hasAttrByPath [ apiVersion type abiVersion ] allArchives.system-images
332
-
instructions = builtins.listToAttrs (map (package: {
333
-
name = package.name;
334
-
value = lib.optionalString (lib.hasPrefix "google_apis" type) ''
335
-
# Patch 'google_apis' system images so they're recognized by the sdk.
336
-
# Without this, `android list targets` shows 'Tag/ABIs : no ABIs' instead
337
-
# of 'Tag/ABIs : google_apis*/*' and the emulator fails with an ABI-related error.
338
-
sed -i '/^Addon.Vendor/d' source.properties
340
-
}) availablePackages
343
-
lib.optionals (availablePackages != [])
344
-
(deployAndroidPackages {
483
+
instructions = builtins.listToAttrs (
485
+
name = package.name;
486
+
value = lib.optionalString (lib.hasPrefix "google_apis" type) ''
487
+
# Patch 'google_apis' system images so they're recognized by the sdk.
488
+
# Without this, `android list targets` shows 'Tag/ABIs : no ABIs' instead
489
+
# of 'Tag/ABIs : google_apis*/*' and the emulator fails with an ABI-related error.
490
+
sed -i '/^Addon.Vendor/d' source.properties
492
+
}) availablePackages
495
+
lib.optionals (availablePackages != [ ]) (deployAndroidPackages {
packages = availablePackages;
patchesInstructions = instructions;
349
-
) platformVersions);
351
-
cmake = map (version:
callPackage ./cmake.nix {
353
-
inherit deployAndroidPackage os arch meta;
507
+
deployAndroidPackage
package = check-version allArchives.packages "cmake" version;
360
-
# Creates a NDK bundle.
361
-
makeNdkBundle = package:
362
-
callPackage ./ndk-bundle {
363
-
inherit deployAndroidPackage os arch platform-tools meta package;
368
-
package = makeNdkBundle (allArchives.packages.ndk-bundle.${ndkVersion} or allArchives.packages.ndk.${ndkVersion});
370
-
lib.optional (shouldLink includeNDK [package]) package
519
+
# Creates a NDK bundle.
522
+
callPackage ./ndk-bundle {
524
+
deployAndroidPackage
537
+
package = makeNdkBundle (
538
+
allArchives.packages.ndk-bundle.${ndkVersion} or allArchives.packages.ndk.${ndkVersion}
541
+
lib.optional (shouldLink includeNDK [ package ]) package
# The "default" NDK bundle.
375
-
ndk-bundle = if ndk-bundles == [] then null else lib.head ndk-bundles;
546
+
ndk-bundle = if ndk-bundles == [ ] then null else lib.head ndk-bundles;
# Makes a Google API bundle.
378
-
google-apis = map (version:
549
+
google-apis = map (
package = (check-version allArchives "addons" version).google_apis;
) (builtins.filter (platformVersion: lib.versionOlder platformVersion "26") platformVersions); # API level 26 and higher include Google APIs by default
384
-
google-tv-addons = map (version:
556
+
google-tv-addons = map (
package = (check-version allArchives "addons" version).google_tv_addon;
···
# This derivation deploys the tools package and symlinks all the desired
# plugins that we want to use. If the license isn't accepted, prints all the licenses
395
-
androidsdk = if !licenseAccepted then throw ''
396
-
${builtins.concatStringsSep "\n\n" (mkLicenseTexts licenseNames)}
569
+
if !licenseAccepted then
571
+
${builtins.concatStringsSep "\n\n" (mkLicenseTexts licenseNames)}
398
-
You must accept the following licenses:
399
-
${lib.concatMapStringsSep "\n" (str: " - ${str}") licenseNames}
573
+
You must accept the following licenses:
574
+
${lib.concatMapStringsSep "\n" (str: " - ${str}") licenseNames}
402
-
by setting nixpkgs config option 'android_sdk.accept_license = true;'.
404
-
by an environment variable for a single invocation of the nix tools.
405
-
$ export NIXPKGS_ACCEPT_ANDROID_SDK_LICENSE=1
406
-
'' else callPackage ./cmdline-tools.nix {
407
-
inherit deployAndroidPackage os arch meta;
577
+
by setting nixpkgs config option 'android_sdk.accept_license = true;'.
579
+
by an environment variable for a single invocation of the nix tools.
580
+
$ export NIXPKGS_ACCEPT_ANDROID_SDK_LICENSE=1
583
+
callPackage ./cmdline-tools.nix {
585
+
deployAndroidPackage
409
-
package = cmdline-tools-package;
591
+
package = cmdline-tools-package;
412
-
# Symlink all requested plugins
413
-
${linkPlugin { name = "platform-tools"; plugin = platform-tools; }}
414
-
${linkPlugin { name = "tools"; plugin = tools; check = toolsVersion != null; }}
415
-
${linkPlugins { name = "build-tools"; plugins = build-tools; }}
416
-
${linkPlugin { name = "emulator"; plugin = emulator; check = includeEmulator; }}
417
-
${linkPlugins { name = "platforms"; plugins = platforms; }}
418
-
${linkPlatformPlugins { name = "sources"; plugins = sources; check = includeSources; }}
419
-
${linkPlugins { name = "cmake"; plugins = cmake; check = includeCmake; }}
420
-
${linkNdkPlugins { name = "ndk-bundle"; rootName = "ndk"; plugins = ndk-bundles; check = includeNDK; }}
421
-
${linkNdkPlugin { name = "ndk-bundle"; plugin = ndk-bundle; check = includeNDK; }}
422
-
${linkSystemImages { images = system-images; check = includeSystemImages; }}
423
-
${linkPlatformPlugins { name = "add-ons"; plugins = google-apis; check = useGoogleAPIs; }}
424
-
${linkPlatformPlugins { name = "add-ons"; plugins = google-tv-addons; check = useGoogleTVAddOns; }}
594
+
# Symlink all requested plugins
596
+
name = "platform-tools";
597
+
plugin = platform-tools;
602
+
check = toolsVersion != null;
605
+
name = "build-tools";
606
+
plugins = build-tools;
611
+
check = includeEmulator;
614
+
name = "platforms";
615
+
plugins = platforms;
617
+
${linkPlatformPlugins {
620
+
check = includeSources;
625
+
check = includeCmake;
628
+
name = "ndk-bundle";
630
+
plugins = ndk-bundles;
631
+
check = includeNDK;
634
+
name = "ndk-bundle";
635
+
plugin = ndk-bundle;
636
+
check = includeNDK;
638
+
${linkSystemImages {
639
+
images = system-images;
640
+
check = includeSystemImages;
642
+
${linkPlatformPlugins {
644
+
plugins = google-apis;
645
+
check = useGoogleAPIs;
647
+
${linkPlatformPlugins {
649
+
plugins = google-tv-addons;
650
+
check = useGoogleTVAddOns;
427
-
${lib.concatMapStrings (identifier:
429
-
package = allArchives.extras.${identifier};
430
-
path = package.path;
431
-
extras = callPackage ./extras.nix {
432
-
inherit deployAndroidPackage package os arch meta;
436
-
targetDir=$(dirname ${path})
437
-
mkdir -p $targetDir
438
-
ln -s ${extras}/libexec/android-sdk/${path} $targetDir
654
+
${lib.concatMapStrings (
657
+
package = allArchives.extras.${identifier};
658
+
path = package.path;
659
+
extras = callPackage ./extras.nix {
661
+
deployAndroidPackage
670
+
targetDir=$(dirname ${path})
671
+
mkdir -p $targetDir
672
+
ln -s ${extras}/libexec/android-sdk/${path} $targetDir
441
-
# Expose common executables in bin/
676
+
# Expose common executables in bin/
444
-
for i in ${platform-tools}/bin/*; do
679
+
for i in ${platform-tools}/bin/*; do
448
-
${lib.optionalString (shouldLink includeEmulator [emulator]) ''
449
-
for i in ${emulator}/bin/*; do
683
+
${lib.optionalString (shouldLink includeEmulator [ emulator ]) ''
684
+
for i in ${emulator}/bin/*; do
454
-
find $ANDROID_SDK_ROOT/${cmdline-tools-package.path}/bin -type f -executable | while read i; do
689
+
find $ANDROID_SDK_ROOT/${cmdline-tools-package.path}/bin -type f -executable | while read i; do
460
-
${lib.concatMapStrings (licenseName:
462
-
licenseHashes = builtins.concatStringsSep "\n" (mkLicenseHashes licenseName);
463
-
licenseHashFile = writeText "androidenv-${licenseName}" licenseHashes;
466
-
ln -s ${licenseHashFile} licenses/${licenseName}
695
+
${lib.concatMapStrings (
698
+
licenseHashes = builtins.concatStringsSep "\n" (mkLicenseHashes licenseName);
699
+
licenseHashFile = writeText "androidenv-${licenseName}" licenseHashes;
702
+
ln -s ${licenseHashFile} licenses/${licenseName}