// Copyright (c) 2026, 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:convert';
import 'dart:io';

import 'package:dartdev/src/executable_compiler.dart';
import 'package:path/path.dart' as p;
import 'package:pub/pub.dart';
import 'package:test/test.dart';

import 'utils.dart';

void main() {
  group('ExecutableCompiler', () {
    test('pathOfSnapshot returns expected path format', () {
      final snapshotPath = ExecutableCompiler.pathOfSnapshot(
        workspaceRoot: '/my/workspace',
        packageName: 'foo',
        relativeScriptPath: p.join('bin', 'bar.dart'),
      );

      expect(
        snapshotPath,
        p.normalize(
          p.join(
            '/my/workspace',
            '.dart_tool',
            'dartdev',
            'bin',
            'foo',
            'bin',
            'bar.dart.snapshot',
          ),
        ),
      );
    });

    test('parseDepfile parses Ninja/Makefile depfiles', () {
      expect(ExecutableCompiler.parseDepfile('target: '), isEmpty);
      expect(ExecutableCompiler.parseDepfile('target:   '), isEmpty);
      expect(ExecutableCompiler.parseDepfile('no colon'), isNull);
      expect(ExecutableCompiler.parseDepfile(r'target: foo.dart\'), isNull);
      expect(
        ExecutableCompiler.parseDepfile('target: foo.dart bar.dart\n'),
        ['foo.dart', 'bar.dart'],
      );
      expect(
        ExecutableCompiler.parseDepfile(r'target: /path\ with/space.dart'),
        ['/path with/space.dart'],
      );
      expect(
        ExecutableCompiler.parseDepfile(r'target: /path\\\ with/space.dart'),
        [r'/path\ with/space.dart'],
      );
      expect(
        ExecutableCompiler.parseDepfile(r'target: c:\\foo\\bar.dart'),
        [r'c:\foo\bar.dart'],
      );
    });

    test('isSnapshotFresh rejects snapshots older than the platform dill', () {
      final dir = Directory.systemTemp.createTempSync('exec_compiler_fresh');
      addTearDown(() => dir.deleteSync(recursive: true));

      File file(String name, String contents) =>
          File(p.join(dir.path, name))..writeAsStringSync(contents);

      // Depfiles escape backslashes and spaces in paths, as the frontend
      // server does when it writes them.
      String escape(String path) =>
          path.replaceAll(r'\', r'\\').replaceAll(' ', r'\ ');

      final source = file('hello.dart', 'void main() {}');
      final packageConfig = file('package_config.json', '{}');
      final platformDill = file('vm_platform.dill', 'platform');
      final snapshot = file('hello.dart.snapshot', 'dill');
      final depfile = file(
        'hello.dart.snapshot${ExecutableCompiler.depfileExtension}',
        '${escape(snapshot.path)}: ${escape(source.path)}\n',
      );
      final metadata = file(
        'hello.dart.snapshot${ExecutableCompiler.metadataExtension}',
        jsonEncode(ExecutableCompiler.buildMetadata(enabledExperiments: [])),
      );

      final now = DateTime.now();
      final earlier = now.subtract(const Duration(seconds: 10));
      for (final input in [source, packageConfig, platformDill]) {
        input.setLastModifiedSync(earlier);
      }
      snapshot.setLastModifiedSync(now);

      bool isFresh() => ExecutableCompiler.isSnapshotFresh(
        snapshotFile: snapshot,
        packageConfigFile: packageConfig,
        depfile: depfile,
        metadataFile: metadata,
        platformDill: platformDill,
        enabledExperiments: [],
      );

      expect(isFresh(), isTrue);

      // A rebuilt SDK keeps the same version string, but its platform dill
      // is newer than snapshots compiled against the previous build.
      platformDill.setLastModifiedSync(now.add(const Duration(seconds: 10)));
      expect(isFresh(), isFalse);

      platformDill.deleteSync();
      expect(isFresh(), isFalse);
    });

    test(
      'compiles executable and reuses snapshot when fresh via depfile',
      () async {
        final pDir = Directory.systemTemp.createTempSync('exec_compiler_test');
        addTearDown(() => pDir.deleteSync(recursive: true));

        final workspaceDir = p.join(pDir.path, 'workspace');
        final pkgDir = p.join(pDir.path, 'pkg');
        Directory(p.join(pkgDir, 'bin')).createSync(recursive: true);
        Directory(p.join(pkgDir, 'lib')).createSync(recursive: true);

        final helperFile = File(p.join(pkgDir, 'lib', 'helper.dart'));
        helperFile.writeAsStringSync(
          'String get message => "Hello from dep!";',
        );

        final scriptFile = File(p.join(pkgDir, 'bin', 'hello.dart'));
        scriptFile.writeAsStringSync('''
import 'package:dep/helper.dart';
void main() => print(message);
''');

        final dotDartTool = Directory(p.join(workspaceDir, '.dart_tool'));
        dotDartTool.createSync(recursive: true);
        final packageConfigFile = File(
          p.join(dotDartTool.path, 'package_config.json'),
        );
        packageConfigFile.writeAsStringSync(
          jsonEncode({
            'configVersion': 2,
            'packages': [
              {
                'name': 'dep',
                'rootUri': p.toUri(pkgDir).toString(),
                'packageUri': 'lib/',
                'languageVersion': '3.0',
              },
            ],
          }),
        );

        final resolved = DartExecutableWithPackageConfig(
          executable: scriptFile.path,
          packageConfig: packageConfigFile.path,
        );

        // First compilation creates snapshot and depfile
        final firstResult = await ExecutableCompiler.compile(
          resolvedExecutable: resolved,
        );

        final expectedSnapshot = ExecutableCompiler.pathOfSnapshot(
          workspaceRoot: workspaceDir,
          packageName: 'dep',
          relativeScriptPath: p.join('bin', 'hello.dart'),
        );
        expect(File(expectedSnapshot).existsSync(), isTrue);

        final depfile = File(
          '$expectedSnapshot${ExecutableCompiler.depfileExtension}',
        );
        expect(depfile.existsSync(), isTrue);
        final deps = ExecutableCompiler.parseDepfile(
          depfile.readAsStringSync(),
        );
        final canonicalDeps = deps?.map(p.canonicalize).toList();
        expect(canonicalDeps, contains(p.canonicalize(scriptFile.path)));
        expect(canonicalDeps, contains(p.canonicalize(helperFile.path)));

        final firstModified = File(expectedSnapshot).lastModifiedSync();

        // Second call reuses cached snapshot because no sources or config changed
        final secondResult = await ExecutableCompiler.compile(
          resolvedExecutable: resolved,
        );
        expect(firstResult.executable, secondResult.executable);
        final secondModified = File(expectedSnapshot).lastModifiedSync();
        expect(firstModified, equals(secondModified));

        // Modifying an imported helper file causes recompilation!
        // Backdate the snapshot timestamp so helperFile is strictly newer.
        File(expectedSnapshot).setLastModifiedSync(
          DateTime.now().subtract(const Duration(seconds: 10)),
        );
        helperFile.setLastModifiedSync(DateTime.now());

        await ExecutableCompiler.compile(
          resolvedExecutable: resolved,
        );
        final thirdModified = File(expectedSnapshot).lastModifiedSync();
        expect(thirdModified.isAfter(firstModified), isTrue);

        // Updating package_config.json also causes recompilation
        File(expectedSnapshot).setLastModifiedSync(
          DateTime.now().subtract(const Duration(seconds: 10)),
        );
        packageConfigFile.setLastModifiedSync(DateTime.now());

        await ExecutableCompiler.compile(
          resolvedExecutable: resolved,
        );
        final fourthModified = File(expectedSnapshot).lastModifiedSync();
        expect(fourthModified.isAfter(thirdModified), isTrue);

        // The metadata records the configuration the snapshot was built with.
        final metadataFile = File(
          '$expectedSnapshot${ExecutableCompiler.metadataExtension}',
        );
        expect(metadataFile.existsSync(), isTrue);
        expect(jsonDecode(metadataFile.readAsStringSync()), {
          'version': ExecutableCompiler.metadataVersion,
          'sdkVersion': ExecutableCompiler.sdkVersion,
          'enabledExperiments': <String>[],
        });

        // Asking for a different set of experiments recompiles, even though
        // nothing on disk changed.
        File(expectedSnapshot).setLastModifiedSync(
          DateTime.now().subtract(const Duration(seconds: 10)),
        );
        final fourthModifiedBackdated = File(
          expectedSnapshot,
        ).lastModifiedSync();
        await ExecutableCompiler.compile(
          resolvedExecutable: resolved,
          enabledExperiments: ['native-assets'],
        );
        final fifthModified = File(expectedSnapshot).lastModifiedSync();
        expect(fifthModified.isAfter(fourthModifiedBackdated), isTrue);
        expect(jsonDecode(metadataFile.readAsStringSync()), {
          'version': ExecutableCompiler.metadataVersion,
          'sdkVersion': ExecutableCompiler.sdkVersion,
          'enabledExperiments': ['native-assets'],
        });

        // ... and asking for them again reuses the snapshot.
        await ExecutableCompiler.compile(
          resolvedExecutable: resolved,
          enabledExperiments: ['native-assets'],
        );
        expect(
          File(expectedSnapshot).lastModifiedSync(),
          equals(fifthModified),
        );

        // A snapshot built by another SDK is not reused.
        File(expectedSnapshot).setLastModifiedSync(
          DateTime.now().subtract(const Duration(seconds: 10)),
        );
        final fifthModifiedBackdated = File(
          expectedSnapshot,
        ).lastModifiedSync();
        metadataFile.writeAsStringSync(
          jsonEncode({
            'version': ExecutableCompiler.metadataVersion,
            'sdkVersion': 'some-other-sdk-version',
            'enabledExperiments': ['native-assets'],
          }),
        );
        await ExecutableCompiler.compile(
          resolvedExecutable: resolved,
          enabledExperiments: ['native-assets'],
        );
        expect(
          File(expectedSnapshot).lastModifiedSync().isAfter(
            fifthModifiedBackdated,
          ),
          isTrue,
        );
      },
    );

    test(
      'sweepStaleTempDirs only removes aged-out temp directories',
      () async {
        final dir = Directory.systemTemp.createTempSync('exec_compiler_sweep');
        addTearDown(() => dir.deleteSync(recursive: true));

        Directory tempDir(String name) =>
            Directory(p.join(dir.path, name))..createSync();

        final abandoned = tempDir('tmpAbandoned');
        File(p.join(abandoned.path, 'leftover.dill')).writeAsStringSync('junk');
        final alsoAbandoned = tempDir('tmpOther');
        // Directories not created by the compiler must never be touched, even
        // though they sit next to the snapshots.
        final unrelated = tempDir('bar');
        final snapshot = File(p.join(dir.path, 'hello.dart.snapshot'))
          ..writeAsStringSync('dill');

        // Nothing is old enough to be swept yet.
        ExecutableCompiler.sweepStaleTempDirs(
          dir,
          maxAge: const Duration(days: 365),
        );
        expect(abandoned.existsSync(), isTrue);
        expect(alsoAbandoned.existsSync(), isTrue);

        // Wait briefly so file modification timestamps are strictly in the past.
        await Future.delayed(const Duration(milliseconds: 50));

        // Everything has now aged out, but only the temp directories go.
        ExecutableCompiler.sweepStaleTempDirs(dir, maxAge: Duration.zero);
        expect(abandoned.existsSync(), isFalse);
        expect(alsoAbandoned.existsSync(), isFalse);
        expect(unrelated.existsSync(), isTrue);
        expect(snapshot.existsSync(), isTrue);
      },
    );

    test('compile removes the temp directory it created', () async {
      final pDir = Directory.systemTemp.createTempSync('exec_compiler_tmp');
      addTearDown(() => pDir.deleteSync(recursive: true));

      final workspaceDir = p.join(pDir.path, 'workspace');
      final fakePubCache = p.join(pDir.path, 'cache');
      final pkgDir = p.join(fakePubCache, 'hosted', 'pub.dev', 'dep-1.0.0');
      Directory(p.join(pkgDir, 'bin')).createSync(recursive: true);

      final scriptFile = File(p.join(pkgDir, 'bin', 'hello.dart'));
      scriptFile.writeAsStringSync('void main() => print("Hello from dep!");');

      final dotDartTool = Directory(p.join(workspaceDir, '.dart_tool'));
      dotDartTool.createSync(recursive: true);
      final packageConfigFile = File(
        p.join(dotDartTool.path, 'package_config.json'),
      );
      packageConfigFile.writeAsStringSync(
        jsonEncode({
          'configVersion': 2,
          'packages': [
            {
              'name': 'dep',
              'rootUri': p.toUri(pkgDir).toString(),
              'packageUri': 'lib/',
              'languageVersion': '3.0',
            },
          ],
        }),
      );

      final snapshotPath = ExecutableCompiler.pathOfSnapshot(
        workspaceRoot: workspaceDir,
        packageName: 'dep',
        relativeScriptPath: p.join('bin', 'hello.dart'),
      );

      await ExecutableCompiler.compile(
        resolvedExecutable: DartExecutableWithPackageConfig(
          executable: scriptFile.path,
          packageConfig: packageConfigFile.path,
        ),
      );

      expect(File(snapshotPath).existsSync(), isTrue);
      final tempParentDir = Directory(
        ExecutableCompiler.pathOfTempDir(workspaceRoot: workspaceDir),
      );
      expect(tempParentDir.existsSync(), isTrue);
      expect(tempParentDir.listSync(), isEmpty);
    });

    test(
      'throws CompilationException when compilation fails and cleans up stale snapshot',
      () async {
        final pDir = Directory.systemTemp.createTempSync(
          'exec_compiler_err_test',
        );
        addTearDown(() => pDir.deleteSync(recursive: true));

        final workspaceDir = p.join(pDir.path, 'workspace');
        final fakePubCache = p.join(pDir.path, 'cache');
        final pkgDir = p.join(fakePubCache, 'hosted', 'pub.dev', 'dep-1.0.0');
        Directory(p.join(pkgDir, 'bin')).createSync(recursive: true);

        final scriptFile = File(p.join(pkgDir, 'bin', 'broken.dart'));
        scriptFile.writeAsStringSync('void main() => print("working");');

        final dotDartTool = Directory(p.join(workspaceDir, '.dart_tool'));
        dotDartTool.createSync(recursive: true);
        final packageConfigFile = File(
          p.join(dotDartTool.path, 'package_config.json'),
        );
        packageConfigFile.writeAsStringSync(
          jsonEncode({
            'configVersion': 2,
            'packages': [
              {
                'name': 'dep',
                'rootUri': p.toUri(pkgDir).toString(),
                'packageUri': 'lib/',
                'languageVersion': '3.0',
              },
            ],
          }),
        );

        final resolved = DartExecutableWithPackageConfig(
          executable: scriptFile.path,
          packageConfig: packageConfigFile.path,
        );

        // First compile succeeds and creates snapshot, depfile, and metadata.
        await ExecutableCompiler.compile(resolvedExecutable: resolved);
        final snapshotPath = ExecutableCompiler.pathOfSnapshot(
          workspaceRoot: workspaceDir,
          packageName: 'dep',
          relativeScriptPath: p.join('bin', 'broken.dart'),
        );
        final snapshotFile = File(snapshotPath);
        final depfile = File(
          '$snapshotPath${ExecutableCompiler.depfileExtension}',
        );
        final metadataFile = File(
          '$snapshotPath${ExecutableCompiler.metadataExtension}',
        );
        expect(snapshotFile.existsSync(), isTrue);
        expect(depfile.existsSync(), isTrue);
        expect(metadataFile.existsSync(), isTrue);

        // Break the script and backdate the snapshot so recompilation runs.
        snapshotFile.setLastModifiedSync(
          DateTime.now().subtract(const Duration(seconds: 10)),
        );
        scriptFile.writeAsStringSync('void main() { this is syntax error }');

        await expectLater(
          () => ExecutableCompiler.compile(
            resolvedExecutable: resolved,
          ),
          throwsA(
            isA<CompilationException>().having(
              (e) => e.message,
              'message',
              allOf(
                contains("Error: 'syntax' isn't a type."),
                isNot(contains('.snapshot.dill')),
              ),
            ),
          ),
        );

        // Stale snapshot, depfile, and metadata should be removed, and no tempDir left.
        expect(snapshotFile.existsSync(), isFalse);
        expect(depfile.existsSync(), isFalse);
        expect(metadataFile.existsSync(), isFalse);
        expect(
          Directory(p.dirname(snapshotPath)).listSync().whereType<Directory>(),
          isEmpty,
        );
      },
    );

    test('end-to-end dart run precompiles and executes dependency', () async {
      final pProject = project(name: 'foo');
      final bar = project(name: 'bar');
      pProject.file('pubspec.yaml', '''
name: foo
environment:
  sdk: '^3.0.0'
dependencies:
  bar:
    path: ${bar.dir.path}
''');
      bar.file('bin/hello.dart', '''
void main(List<String> args) {
  print("Hello from bar:hello \${args.join(' ')}");
}
''');

      final result = await pProject.run(['run', 'bar:hello', 'arg1', 'arg2']);
      expect(result.exitCode, 0);
      expect(result.stdout, contains('Hello from bar:hello arg1 arg2'));
      final snapshot = File(
        ExecutableCompiler.pathOfSnapshot(
          workspaceRoot: pProject.dirPath,
          packageName: 'bar',
          relativeScriptPath: p.join('bin', 'hello.dart'),
        ),
      );
      expect(snapshot.existsSync(), isTrue);
    });

    test(
      'end-to-end dart run reports the built executable only with -v',
      () async {
        Future<ProcessResult> runFreshProject(List<String> arguments) {
          final pProject = project(name: 'foo');
          final bar = project(name: 'bar');
          pProject.file('pubspec.yaml', '''
name: foo
environment:
  sdk: '^3.0.0'
dependencies:
  bar:
    path: ${bar.dir.path}
''');
          bar.file('bin/hello.dart', '''
void main(List<String> args) {
  print("Hello from bar:hello");
}
''');
          return pProject.run(['run', ...arguments, 'bar:hello']);
        }

        final verboseResult = await runFreshProject(['-v']);
        expect(verboseResult.exitCode, 0);
        expect(verboseResult.stderr, contains('Built bar:hello.'));
        expect(verboseResult.stdout, isNot(contains('Built bar:hello.')));

        final result = await runFreshProject([]);
        expect(result.exitCode, 0);
        expect(result.stderr, isNot(contains('Built')));
        expect(result.stdout.trim(), 'Hello from bar:hello');
      },
    );

    test('end-to-end dart run respects --verbosity=error', () async {
      final pProject = project(name: 'foo');
      final bar = project(name: 'bar');
      pProject.file('pubspec.yaml', '''
name: foo
environment:
  sdk: '^3.0.0'
dependencies:
  bar:
    path: ${bar.dir.path}
''');
      bar.file('bin/hello.dart', '''
void main(List<String> args) {
  print("Hello from bar:hello");
}
''');
      final result = await pProject.run([
        'run',
        '--verbosity=error',
        'bar:hello',
      ]);
      expect(result.exitCode, 0);
      expect(result.stderr, isEmpty);
      expect(result.stdout.trim(), equals('Hello from bar:hello'));
    });

    test(
      'end-to-end dart run preserves Platform.script with spaces in path',
      () async {
        final pProject = project(name: 'foo');
        final barDirWithSpace = Directory(
          p.join(pProject.dirPath, 'deps with space', 'bar'),
        )..createSync(recursive: true);
        File(p.join(barDirWithSpace.path, 'pubspec.yaml')).writeAsStringSync('''
name: bar
environment:
  sdk: '^3.0.0'
''');
        Directory(
          p.join(barDirWithSpace.path, 'bin'),
        ).createSync(recursive: true);
        final scriptProbeFile = File(
          p.join(barDirWithSpace.path, 'bin', 'script_probe.dart'),
        );
        scriptProbeFile.writeAsStringSync('''
import 'dart:io';

void main() {
  print("SCRIPT: \${Platform.script.toFilePath()}");
}
''');

        pProject.file('pubspec.yaml', '''
name: foo
environment:
  sdk: '^3.0.0'
dependencies:
  bar:
    path: ${barDirWithSpace.path}
''');

        final result = await pProject.run([
          'run',
          '--verbosity=error',
          'bar:script_probe',
        ]);
        expect(result.exitCode, 0);
        final expectedPath = p.canonicalize(scriptProbeFile.path);
        expect(result.stdout, startsWith('SCRIPT: '));
        expect(
          p.canonicalize(result.stdout.trim().substring('SCRIPT: '.length)),
          equals(expectedPath),
        );
        expect(result.stdout, isNot(contains('.snapshot')));
        expect(result.stdout, isNot(contains('"')));
      },
    );

    test(
      'incremental recompilation reuses existing snapshot when source is modified',
      () async {
        final pProject = project(name: 'foo');
        final bar = project(name: 'bar');
        pProject.file('pubspec.yaml', '''
name: foo
environment:
  sdk: '^3.0.0'
dependencies:
  bar:
    path: ${bar.dir.path}
''');
        bar.file('bin/hello.dart', '''
void main() {
  print("Hello 1");
}
''');

        var result = await pProject.run([
          'run',
          '--verbosity=error',
          'bar:hello',
        ]);
        expect(result.exitCode, 0);
        expect(result.stdout.trim(), equals('Hello 1'));

        final snapshot = File(
          ExecutableCompiler.pathOfSnapshot(
            workspaceRoot: pProject.dirPath,
            packageName: 'bar',
            relativeScriptPath: p.join('bin', 'hello.dart'),
          ),
        );
        expect(snapshot.existsSync(), isTrue);

        // Backdate snapshot before modifying source so timestamp is strictly newer.
        snapshot.setLastModifiedSync(
          DateTime.now().subtract(const Duration(seconds: 10)),
        );

        // Modify the source code
        bar.file('bin/hello.dart', '''
void main() {
  print("Hello 2");
}
''');

        result = await pProject.run(['run', '--verbosity=error', 'bar:hello']);
        expect(result.exitCode, 0);
        expect(result.stdout.trim(), equals('Hello 2'));
      },
    );

    test(
      'dart --enable-experiment=<exp> run caches and reuses experiment metadata',
      () async {
        final pProject = project(name: 'foo');
        final bar = project(name: 'bar');
        pProject.file('pubspec.yaml', '''
name: foo
environment:
  sdk: '^3.0.0'
dependencies:
  bar:
    path: ${bar.dir.path}
''');
        bar.file('bin/hello.dart', '''
void main() {
  print("Hello experiment");
}
''');

        // Pass --enable-experiment as a global/VM flag before 'run'
        final result = await pProject.run([
          '--enable-experiment=test-experiment',
          'run',
          '--verbosity=error',
          'bar:hello',
        ]);
        expect(result.exitCode, 0);
        expect(result.stdout.trim(), equals('Hello experiment'));

        final snapshotPath = ExecutableCompiler.pathOfSnapshot(
          workspaceRoot: pProject.dirPath,
          packageName: 'bar',
          relativeScriptPath: p.join('bin', 'hello.dart'),
        );
        final metadataFile = File(
          '$snapshotPath${ExecutableCompiler.metadataExtension}',
        );
        expect(metadataFile.existsSync(), isTrue);
        expect(jsonDecode(metadataFile.readAsStringSync()), {
          'version': ExecutableCompiler.metadataVersion,
          'sdkVersion': ExecutableCompiler.sdkVersion,
          'enabledExperiments': ['test-experiment'],
        });
      },
    );

    test(
      'scripts with the same basename in different subdirectories do not collide',
      () async {
        final pDir = Directory.systemTemp.createTempSync(
          'exec_compiler_collision_test',
        );
        addTearDown(() => pDir.deleteSync(recursive: true));

        final workspaceDir = p.join(pDir.path, 'workspace');
        final pkgDir = p.join(pDir.path, 'pkg');
        Directory(p.join(pkgDir, 'bin')).createSync(recursive: true);
        Directory(p.join(pkgDir, 'tool')).createSync(recursive: true);

        final binScript = File(p.join(pkgDir, 'bin', 'main.dart'))
          ..writeAsStringSync('void main() => print("From bin/main.dart");');
        final toolScript = File(p.join(pkgDir, 'tool', 'main.dart'))
          ..writeAsStringSync('void main() => print("From tool/main.dart");');

        final dotDartTool = Directory(p.join(workspaceDir, '.dart_tool'))
          ..createSync(recursive: true);
        final packageConfigFile = File(
          p.join(dotDartTool.path, 'package_config.json'),
        );
        packageConfigFile.writeAsStringSync(
          jsonEncode({
            'configVersion': 2,
            'packages': [
              {
                'name': 'foo',
                'rootUri': p.toUri(pkgDir).toString(),
                'packageUri': 'lib/',
                'languageVersion': '3.0',
              },
            ],
          }),
        );

        final resBin = await ExecutableCompiler.compile(
          resolvedExecutable: DartExecutableWithPackageConfig(
            executable: binScript.path,
            packageConfig: packageConfigFile.path,
          ),
        );
        final resTool = await ExecutableCompiler.compile(
          resolvedExecutable: DartExecutableWithPackageConfig(
            executable: toolScript.path,
            packageConfig: packageConfigFile.path,
          ),
        );

        expect(resBin.executable, isNot(equals(resTool.executable)));

        final binSnapshot = File(
          ExecutableCompiler.pathOfSnapshot(
            workspaceRoot: workspaceDir,
            packageName: 'foo',
            relativeScriptPath: p.join('bin', 'main.dart'),
          ),
        );
        final toolSnapshot = File(
          ExecutableCompiler.pathOfSnapshot(
            workspaceRoot: workspaceDir,
            packageName: 'foo',
            relativeScriptPath: p.join('tool', 'main.dart'),
          ),
        );
        expect(binSnapshot.existsSync(), isTrue);
        expect(toolSnapshot.existsSync(), isTrue);
      },
    );
  });
}
