in lib/src/entrypoint.dart [744:841]
void _checkPackageConfigUpToDate() {
void outOfDate() {
dataError('The $lockFilePath file has changed since the '
'$packageConfigFile file '
'was generated, please run "$topLevelProgram pub get" again.');
}
void badPackageConfig() {
dataError('The "$packageConfigFile" file is not recognized by '
'"pub" version, please run "$topLevelProgram pub get".');
}
late String packageConfigRaw;
try {
packageConfigRaw = readTextFile(packageConfigFile);
} on FileException {
dataError(
'The "$packageConfigFile" file does not exist, please run "$topLevelProgram pub get".');
}
late PackageConfig cfg;
try {
cfg = PackageConfig.fromJson(json.decode(packageConfigRaw));
} on FormatException {
badPackageConfig();
}
// Version 2 is the initial version number for `package_config.json`,
// because `.packages` was version 1 (even if it was a different file).
// If the version is different from 2, then it must be a newer incompatible
// version, hence, the user should run `pub get` with the downgraded SDK.
if (cfg.configVersion != 2) {
badPackageConfig();
}
final packagePathsMapping = <String, String>{};
// We allow the package called 'flutter_gen' to be injected into
// package_config.
//
// This is somewhat a hack. But it allows flutter to generate code in a
// package as it likes.
//
// See https://github.com/flutter/flutter/issues/73870 .
final packagesToCheck =
cfg.packages.where((package) => package.name != 'flutter_gen');
for (final pkg in packagesToCheck) {
// Pub always makes a packageUri of lib/
if (pkg.packageUri == null || pkg.packageUri.toString() != 'lib/') {
badPackageConfig();
}
packagePathsMapping[pkg.name] =
root.path('.dart_tool', p.fromUri(pkg.rootUri));
}
if (!_isPackagePathsMappingUpToDateWithLockfile(packagePathsMapping)) {
outOfDate();
}
// Check if language version specified in the `package_config.json` is
// correct. This is important for path dependencies as these can mutate.
for (final pkg in cfg.packages) {
if (pkg.name == root.name || pkg.name == 'flutter_gen') continue;
final id = lockFile.packages[pkg.name];
if (id == null) {
assert(
false,
'unnecessary package_config.json entries should be forbidden by '
'_isPackagePathsMappingUpToDateWithLockfile',
);
continue;
}
// If a package is cached, then it's universally immutable and we need
// not check if the language version is correct.
final source = cache.source(id.source);
if (source is CachedSource) {
continue;
}
try {
// Load `pubspec.yaml` and extract language version to compare with the
// language version from `package_config.json`.
final languageVersion = LanguageVersion.fromSdkConstraint(
cache.load(id).pubspec.sdkConstraints[sdk.identifier],
);
if (pkg.languageVersion != languageVersion) {
final relativePubspecPath = p.join(
source.getDirectory(id, relativeFrom: '.'), 'pubspec.yaml');
dataError('$relativePubspecPath has '
'changed since the $lockFilePath file was generated, please run '
'"$topLevelProgram pub get" again.');
}
} on FileException {
dataError('Failed to read pubspec.yaml for "${pkg.name}", perhaps the '
'entry is missing, please run "$topLevelProgram pub get".');
}
}
}