// Copyright 2014 The Flutter Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. import 'package:file/memory.dart'; import 'package:flutter_tools/src/asset.dart'; import 'package:flutter_tools/src/base/file_system.dart'; import 'package:flutter_tools/src/build_info.dart'; import 'package:flutter_tools/src/cache.dart'; import 'package:flutter_tools/src/globals.dart' as globals; import '../src/common.dart'; import '../src/context.dart'; void main() { group('Assets', () { final String dataPath = globals.fs.path.join( getFlutterRoot(), 'packages', 'flutter_tools', 'test', 'data', 'asset_test', ); setUpAll(() { Cache.disableLocking(); }); // This test intentionally does not use a memory file system to ensure // that AssetBundle with fonts also works on Windows. testUsingContext('app font uses local font file', () async { final AssetBundle asset = AssetBundleFactory.instance.createBundle(); final String manifestPath = globals.fs.path.join(dataPath, 'main', 'pubspec.yaml'); final String packagesPath = globals.fs.path.join(dataPath, 'main', '.packages'); await asset.build( manifestPath: manifestPath, packagesPath: packagesPath, ); expect(asset.entries.containsKey('FontManifest.json'), isTrue); expect( await getValueAsString('FontManifest.json', asset), '[{"family":"packages/font/test_font","fonts":[{"asset":"packages/font/test_font_file"}]}]', ); expect(asset.wasBuiltOnce(), true); expect( asset.inputFiles.map((File f) { return f.path; }), <String>[ packagesPath, globals.fs.path.join(dataPath, 'font', 'pubspec.yaml'), manifestPath, globals.fs.path.join(dataPath, 'font', 'test_font_file'), ], ); }); testUsingContext('handles empty pubspec with .packages', () async { final String dataPath = globals.fs.path.join( getFlutterRoot(), 'packages', 'flutter_tools', 'test', 'data', 'fuchsia_test', ); final AssetBundle asset = AssetBundleFactory.instance.createBundle(); await asset.build( manifestPath: globals.fs.path .join(dataPath, 'main', 'pubspec.yaml'), // file doesn't exist packagesPath: globals.fs.path.join(dataPath, 'main', '.packages'), ); expect(asset.wasBuiltOnce(), true); expect( asset.inputFiles.map((File f) { return f.path; }), <String>[], ); }); }); const String packageConfig = ''' { "configVersion": 2, "packages":[ { "name": "my_package", "rootUri": "file:///", "packageUri": "lib/", "languageVersion": "2.17" } ] } '''; const String pubspecDotYaml = ''' name: my_package '''; testUsingContext('Bundles material shaders on non-web platforms', () async { final String shaderPath = globals.fs.path.join( Cache.flutterRoot!, 'packages', 'flutter', 'lib', 'src', 'material', 'shaders', 'ink_sparkle.frag' ); globals.fs.file(shaderPath).createSync(recursive: true); globals.fs.file('.dart_tool/package_config.json') ..createSync(recursive: true) ..writeAsStringSync(packageConfig); globals.fs.file('pubspec.yaml').writeAsStringSync(pubspecDotYaml); final AssetBundle asset = AssetBundleFactory.instance.createBundle(); await asset.build(packagesPath: '.packages', targetPlatform: TargetPlatform.android_arm); expect(asset.entries.keys, contains('shaders/ink_sparkle.frag')); }, overrides: <Type, Generator>{ FileSystem: () => MemoryFileSystem.test(), ProcessManager: () => FakeProcessManager.empty(), }); testUsingContext('Does bundle material shaders on web platforms', () async { final String shaderPath = globals.fs.path.join( Cache.flutterRoot!, 'packages', 'flutter', 'lib', 'src', 'material', 'shaders', 'ink_sparkle.frag' ); globals.fs.file(shaderPath).createSync(recursive: true); globals.fs.file('.dart_tool/package_config.json') ..createSync(recursive: true) ..writeAsStringSync(packageConfig); globals.fs.file('pubspec.yaml').writeAsStringSync(pubspecDotYaml); final AssetBundle asset = AssetBundleFactory.instance.createBundle(); await asset.build(packagesPath: '.packages', targetPlatform: TargetPlatform.web_javascript); expect(asset.entries.keys, contains('shaders/ink_sparkle.frag')); }, overrides: <Type, Generator>{ FileSystem: () => MemoryFileSystem.test(), ProcessManager: () => FakeProcessManager.empty(), }); } Future<String> getValueAsString(String key, AssetBundle asset) async { return String.fromCharCodes(await asset.entries[key]!.contentsAsBytes()); }