Skip to content

[native_assets_cli] AssetDownloader #996

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
dcharkes opened this issue Mar 12, 2024 · 2 comments
Open

[native_assets_cli] AssetDownloader #996

dcharkes opened this issue Mar 12, 2024 · 2 comments
Labels
P3 A lower priority bug or feature request package:hooks

Comments

@dcharkes
Copy link
Collaborator

I'm punting this from package:native_assets_cli.

This should likely live in a separate helper package.

// Copyright (c) 2024, the Dart project authors.  Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

import 'dart:io';

import 'package:logging/logging.dart';

import '../../native_assets_cli.dart';

abstract class Builder {
  Future<void> run({
    required BuildConfig config,
    required BuildOutput output,
    required Logger? logger,
  });
}

// TODO(dacoharkes): Should we really add this? It seems too specific.
// E.g. what about varying file names, zipped downloads etc. etc. ?
class AssetDownloader implements Builder {
  final Uri Function(OS, Architecture) downloadUri;

  /// Asset identifier.
  ///
  /// If omitted, no asset will be added to the build output.
  final String assetName;

  AssetDownloader({
    required this.downloadUri,
    required this.assetName,
  });

  @override
  Future<void> run({
    required BuildConfig config,
    required BuildOutput output,
    required Logger? logger,
  }) async {
    Uri? targetUri;
    if (!config.dryRun) {
      final downloadUri2 = downloadUri(
        config.targetOS,
        config.targetArchitecture!,
      );
      final fileName =
          downloadUri2.pathSegments.lastWhere((element) => element.isNotEmpty);
      targetUri = config.outputDirectory.resolve(fileName);
      final request = await HttpClient().getUrl(downloadUri2);
      final response = await request.close();
      await response.pipe(File.fromUri(targetUri).openWrite());
    }

    output.addAsset(
      CCodeAsset(
        package: config.packageName,
        name: assetName,
        file: targetUri,
        linkMode: LinkMode.dynamic,
        dynamicLoading: BundledDylib(),
        os: config.targetOS,
        architecture: config.targetArchitecture,
      ),
    );
  }
}

It might implement the shared interface Builder:

@dcharkes
Copy link
Collaborator Author

Also an interesting feature: Take an optional SHA256 hash to check against. Doesn't need to be implemented in this PR though.

@knopp
Copy link
Contributor

knopp commented May 23, 2024

In cargokit (project I'm hoping to retire the moment native assets are no longer experimental) I use private / public key to check the downloaded binaries. The public key is part of dart package, and when downloading binaries a ed25519_edwards signature is downloaded alongside to verify that the binary was built by the github workflow (the repository has access to private key as a github secret).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
P3 A lower priority bug or feature request package:hooks
Projects
None yet
Development

No branches or pull requests

2 participants