Future prepareWorkspace()

in build_runner_core/lib/src/generate/build_definition.dart [208:298]


  Future<BuildDefinition> prepareWorkspace() async {
    _checkBuildPhases();

    _logger.info('Initializing inputs');

    var assetGraph = await _tryReadCachedAssetGraph();
    var assetTracker = AssetTracker(_environment.reader, _options.targetGraph);
    var inputSources = await assetTracker._findInputSources();
    var cacheDirSources = await assetTracker._findCacheDirSources();
    var internalSources = await assetTracker._findInternalSources();

    BuildScriptUpdates? buildScriptUpdates;
    if (assetGraph != null) {
      var updates = await logTimedAsync(
          _logger,
          'Checking for updates since last build',
          () => _updateAssetGraph(assetGraph!, assetTracker, _buildPhases,
              inputSources, cacheDirSources, internalSources));
      buildScriptUpdates = await BuildScriptUpdates.create(
          _environment.reader, _options.packageGraph, assetGraph,
          disabled: _options.skipBuildScriptCheck);

      var buildScriptUpdated = !_options.skipBuildScriptCheck &&
          buildScriptUpdates.hasBeenUpdated(updates.keys.toSet());
      if (buildScriptUpdated) {
        _logger.warning('Invalidating asset graph due to build script update!');

        var deletedSourceOutputs = await _cleanupOldOutputs(assetGraph);

        if (_runningFromSnapshot) {
          // We have to be regenerated if running from a snapshot.
          throw BuildScriptChangedException();
        }

        inputSources.removeAll(deletedSourceOutputs);
        assetGraph = null;
        buildScriptUpdates = null;
      }
    }

    if (assetGraph == null) {
      late Set<AssetId> conflictingOutputs;

      await logTimedAsync(_logger, 'Building new asset graph', () async {
        try {
          assetGraph = await AssetGraph.build(_buildPhases, inputSources,
              internalSources, _options.packageGraph, _environment.reader);
        } on DuplicateAssetNodeException catch (e, st) {
          _logger.severe('Conflicting outputs', e, st);
          throw CannotBuildException();
        }
        buildScriptUpdates = await BuildScriptUpdates.create(
            _environment.reader, _options.packageGraph, assetGraph!,
            disabled: _options.skipBuildScriptCheck);

        conflictingOutputs = assetGraph!.outputs
            .where((n) => n.package == _options.packageGraph.root.name)
            .where(inputSources.contains)
            .toSet();
        final conflictsInDeps = assetGraph!.outputs
            .where((n) => n.package != _options.packageGraph.root.name)
            .where(inputSources.contains)
            .toSet();
        if (conflictsInDeps.isNotEmpty) {
          log.severe('There are existing files in dependencies which conflict '
              'with files that a Builder may produce. These must be removed or '
              'the Builders disabled before a build can continue: '
              '${conflictsInDeps.map((a) => a.uri).join('\n')}');
          throw CannotBuildException();
        }
      });

      await logTimedAsync(
          _logger,
          'Checking for unexpected pre-existing outputs.',
          () => _initialBuildCleanup(conflictingOutputs,
              _wrapWriter(_environment.writer, assetGraph!)));
    }

    return BuildDefinition._(
        assetGraph!,
        _options.targetGraph,
        _wrapReader(_environment.reader, assetGraph!),
        _wrapWriter(_environment.writer, assetGraph!),
        _options.packageGraph,
        _options.deleteFilesByDefault,
        ResourceManager(),
        buildScriptUpdates,
        _options.enableLowResourcesMode,
        _environment);
  }