| // Copyright (c) 2018, 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 'package:analyzer/src/dart/analysis/experiments.dart'; |
| import 'package:analyzer/src/dart/analysis/experiments_impl.dart'; |
| import 'package:meta/meta.dart'; |
| import 'package:pub_semver/pub_semver.dart'; |
| import 'package:test/test.dart'; |
| import 'package:test_reflective_loader/test_reflective_loader.dart'; |
| |
| main() { |
| defineReflectiveSuite(() { |
| defineReflectiveTests(ExperimentsTest); |
| }); |
| } |
| |
| @reflectiveTest |
| class ExperimentsTest { |
| var knownFeatures = <String, ExperimentalFeature>{}; |
| |
| void assertLatestSdkLanguageVersion(ExperimentStatus status) { |
| expect( |
| getSdkLanguageVersion(status), |
| ExperimentStatus.latestSdkLanguageVersion, |
| ); |
| } |
| |
| void assertSdkLanguageVersion(ExperimentStatus status, String expectedStr) { |
| var actual = getSdkLanguageVersion(status); |
| expect('${actual.major}.${actual.minor}', expectedStr); |
| } |
| |
| ExperimentStatus fromStrings(List<String> flags) { |
| return overrideKnownFeatures( |
| knownFeatures, () => ExperimentStatus.fromStrings(flags)); |
| } |
| |
| ExperimentStatus fromStrings2({ |
| @required Version sdkLanguageVersion, |
| @required List<String> flags, |
| }) { |
| return overrideKnownFeatures(knownFeatures, () { |
| return ExperimentStatus.fromStrings2( |
| sdkLanguageVersion: sdkLanguageVersion, |
| flags: flags, |
| ); |
| }); |
| } |
| |
| List<bool> getFlags(ExperimentStatus status) { |
| return getExperimentalFlags_forTesting(status); |
| } |
| |
| Version getSdkLanguageVersion(ExperimentStatus status) { |
| return getSdkLanguageVersion_forTesting(status); |
| } |
| |
| List<ConflictingFlagLists> getValidateCombinationResult( |
| List<String> flags1, List<String> flags2) { |
| return overrideKnownFeatures( |
| knownFeatures, () => validateFlagCombination(flags1, flags2).toList()); |
| } |
| |
| List<ValidationResult> getValidationResult(List<String> flags) { |
| return overrideKnownFeatures( |
| knownFeatures, () => validateFlags(flags).toList()); |
| } |
| |
| test_currentVersion() { |
| // We don't care what the current version is, we just want to make sure that |
| // it parses without error, and that it takes a simple 'major.minor' form. |
| var currentVersion = ExperimentStatus.currentVersion; |
| expect(currentVersion.patch, 0); |
| expect(currentVersion.preRelease, isEmpty); |
| expect(currentVersion.build, isEmpty); |
| } |
| |
| test_fromStrings2_experimentalReleased_shouldBe_requested() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.2.0'), |
| ); |
| knownFeatures['b'] = ExperimentalFeature( |
| index: 1, |
| enableString: 'b', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'b', |
| experimentalReleaseVersion: Version.parse('1.4.0'), |
| releaseVersion: null, |
| ); |
| knownFeatures['c'] = ExperimentalFeature( |
| index: 2, |
| enableString: 'c', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'c', |
| experimentalReleaseVersion: Version.parse('1.4.0'), |
| releaseVersion: null, |
| ); |
| overrideKnownFeatures(knownFeatures, () { |
| // Only experiments that are explicitly requested can be enabled. |
| var status = fromStrings2( |
| sdkLanguageVersion: Version.parse('1.5.0'), |
| flags: ['b'], |
| ); |
| assertSdkLanguageVersion(status, '1.5'); |
| expect(getFlags(status), [true, true, false]); |
| }); |
| } |
| |
| test_fromStrings2_flags_conflicting_disable_then_enable() { |
| // Enable takes precedence because it's last |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var status = fromStrings2( |
| sdkLanguageVersion: ExperimentStatus.latestSdkLanguageVersion, |
| flags: ['no-a', 'a'], |
| ); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [true]); |
| } |
| |
| test_fromStrings2_flags_conflicting_enable_then_disable() { |
| // Disable takes precedence because it's last |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var status = fromStrings2( |
| sdkLanguageVersion: ExperimentStatus.latestSdkLanguageVersion, |
| flags: ['a', 'no-a'], |
| ); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [false]); |
| } |
| |
| test_fromStrings2_flags_disable_disabled_feature() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var status = fromStrings2( |
| sdkLanguageVersion: ExperimentStatus.latestSdkLanguageVersion, |
| flags: ['no-a'], |
| ); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [false]); |
| } |
| |
| test_fromStrings2_flags_disable_enabled_feature() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| var status = fromStrings2( |
| sdkLanguageVersion: ExperimentStatus.latestSdkLanguageVersion, |
| flags: ['no-a'], |
| ); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [false]); |
| } |
| |
| test_fromStrings2_flags_empty() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| knownFeatures['b'] = ExperimentalFeature( |
| index: 1, |
| enableString: 'b', |
| isEnabledByDefault: true, |
| isExpired: false, |
| documentation: 'b', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| var status = fromStrings2( |
| sdkLanguageVersion: ExperimentStatus.latestSdkLanguageVersion, |
| flags: [], |
| ); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [false, true]); |
| } |
| |
| test_fromStrings2_flags_enable_disabled_feature() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var status = fromStrings2( |
| sdkLanguageVersion: ExperimentStatus.latestSdkLanguageVersion, |
| flags: ['a'], |
| ); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [true]); |
| } |
| |
| test_fromStrings2_flags_enable_enabled_feature() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| var status = fromStrings2( |
| sdkLanguageVersion: ExperimentStatus.latestSdkLanguageVersion, |
| flags: ['a'], |
| ); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [true]); |
| } |
| |
| test_fromStrings2_flags_illegal_use_of_expired_disable() { |
| // Expired flags are ignored even if they would fail validation. |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: true, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| var status = fromStrings2( |
| sdkLanguageVersion: ExperimentStatus.latestSdkLanguageVersion, |
| flags: ['no-a'], |
| ); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [true]); |
| } |
| |
| test_fromStrings2_flags_illegal_use_of_expired_enable() { |
| // Expired flags are ignored even if they would fail validation. |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: true, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var status = fromStrings2( |
| sdkLanguageVersion: ExperimentStatus.latestSdkLanguageVersion, |
| flags: ['a'], |
| ); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [false]); |
| } |
| |
| test_fromStrings2_flags_unnecessary_use_of_expired_disable() { |
| // Expired flags are ignored. |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: true, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var status = fromStrings2( |
| sdkLanguageVersion: ExperimentStatus.latestSdkLanguageVersion, |
| flags: ['no-a'], |
| ); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [false]); |
| } |
| |
| test_fromStrings2_flags_unnecessary_use_of_expired_enable() { |
| // Expired flags are ignored. |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: true, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| var status = fromStrings2( |
| sdkLanguageVersion: ExperimentStatus.latestSdkLanguageVersion, |
| flags: ['a'], |
| ); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [true]); |
| } |
| |
| test_fromStrings2_flags_unrecognized() { |
| // Unrecognized flags are ignored. |
| var status = fromStrings2( |
| sdkLanguageVersion: ExperimentStatus.latestSdkLanguageVersion, |
| flags: ['a'], |
| ); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), <Object>[]); |
| } |
| |
| test_fromStrings2_sdkLanguage_allows_experimental() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.2.0'), |
| ); |
| knownFeatures['b'] = ExperimentalFeature( |
| index: 1, |
| enableString: 'b', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'b', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| knownFeatures['c'] = ExperimentalFeature( |
| index: 2, |
| enableString: 'c', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'c', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| overrideKnownFeatures(knownFeatures, () { |
| var status = fromStrings2( |
| sdkLanguageVersion: Version.parse('1.5.0'), |
| flags: ['b', 'c'], |
| ); |
| assertSdkLanguageVersion(status, '1.5'); |
| expect(getFlags(status), [true, true, true]); |
| |
| // Restricting to the SDK version does not change anything. |
| var status2 = status.restrictToVersion(Version.parse('1.5.0')); |
| assertSdkLanguageVersion(status2, '1.5'); |
| expect(getFlags(status2), [true, true, true]); |
| |
| // Restricting to the previous version disables the experiments. |
| var status3 = status.restrictToVersion(Version.parse('1.4.0')); |
| assertSdkLanguageVersion(status3, '1.5'); |
| expect(getFlags(status3), [true, false, false]); |
| }); |
| } |
| |
| test_fromStrings2_sdkLanguage_allows_experimentalReleased() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.2.0'), |
| ); |
| knownFeatures['b'] = ExperimentalFeature( |
| index: 1, |
| enableString: 'b', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'b', |
| experimentalReleaseVersion: Version.parse('1.4.0'), |
| releaseVersion: null, |
| ); |
| knownFeatures['c'] = ExperimentalFeature( |
| index: 2, |
| enableString: 'c', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'c', |
| experimentalReleaseVersion: Version.parse('1.5.0'), |
| releaseVersion: null, |
| ); |
| knownFeatures['d'] = ExperimentalFeature( |
| index: 3, |
| enableString: 'd', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'd', |
| experimentalReleaseVersion: Version.parse('1.6.0'), |
| releaseVersion: null, |
| ); |
| overrideKnownFeatures(knownFeatures, () { |
| var status = fromStrings2( |
| sdkLanguageVersion: Version.parse('1.5.0'), |
| flags: ['b', 'c', 'd'], |
| ); |
| assertSdkLanguageVersion(status, '1.5'); |
| expect(getFlags(status), [true, true, true, true]); |
| |
| // Restricting to the SDK version does not change anything. |
| var status2 = status.restrictToVersion(Version.parse('1.5.0')); |
| assertSdkLanguageVersion(status2, '1.5'); |
| expect(getFlags(status2), [true, true, true, true]); |
| |
| // Restricting to a version disables some experiments. |
| var status3 = status.restrictToVersion(Version.parse('1.4.0')); |
| assertSdkLanguageVersion(status3, '1.5'); |
| expect(getFlags(status3), [true, true, false, false]); |
| }); |
| } |
| |
| test_fromStrings2_sdkLanguage_restricts_released() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.6.0'), |
| ); |
| knownFeatures['b'] = ExperimentalFeature( |
| index: 1, |
| enableString: 'b', |
| isEnabledByDefault: true, |
| isExpired: false, |
| documentation: 'b', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.1.0'), |
| ); |
| var status = fromStrings2( |
| sdkLanguageVersion: Version.parse('1.5.0'), |
| flags: [], |
| ); |
| assertSdkLanguageVersion(status, '1.5'); |
| expect(getFlags(status), [false, true]); |
| } |
| |
| test_fromStrings_conflicting_flags_disable_then_enable() { |
| // Enable takes precedence because it's last |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var status = fromStrings(['no-a', 'a']); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [true]); |
| } |
| |
| test_fromStrings_conflicting_flags_enable_then_disable() { |
| // Disable takes precedence because it's last |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var status = fromStrings(['a', 'no-a']); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [false]); |
| } |
| |
| test_fromStrings_default_values() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| knownFeatures['b'] = ExperimentalFeature( |
| index: 1, |
| enableString: 'b', |
| isEnabledByDefault: true, |
| isExpired: false, |
| documentation: 'b', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| var status = fromStrings([]); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [false, true]); |
| } |
| |
| test_fromStrings_disable_disabled_feature() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var status = fromStrings(['no-a']); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [false]); |
| } |
| |
| test_fromStrings_disable_enabled_feature() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| var status = fromStrings(['no-a']); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [false]); |
| } |
| |
| test_fromStrings_enable_disabled_feature() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var status = fromStrings(['a']); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [true]); |
| } |
| |
| test_fromStrings_enable_enabled_feature() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| var status = fromStrings(['a']); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [true]); |
| } |
| |
| test_fromStrings_illegal_use_of_expired_flag_disable() { |
| // Expired flags are ignored even if they would fail validation. |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: true, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| var status = fromStrings(['no-a']); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [true]); |
| } |
| |
| test_fromStrings_illegal_use_of_expired_flag_enable() { |
| // Expired flags are ignored even if they would fail validation. |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: true, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var status = fromStrings(['a']); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [false]); |
| } |
| |
| test_fromStrings_unnecessary_use_of_expired_flag_disable() { |
| // Expired flags are ignored. |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: true, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var status = fromStrings(['no-a']); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [false]); |
| } |
| |
| test_fromStrings_unnecessary_use_of_expired_flag_enable() { |
| // Expired flags are ignored. |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: true, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| var status = fromStrings(['a']); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), [true]); |
| } |
| |
| test_fromStrings_unrecognized_flag() { |
| // Unrecognized flags are ignored. |
| var status = fromStrings(['a']); |
| assertLatestSdkLanguageVersion(status); |
| expect(getFlags(status), <Object>[]); |
| } |
| |
| test_validateFlagCombination_disable_then_enable() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| knownFeatures['b'] = ExperimentalFeature( |
| index: 1, |
| enableString: 'b', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'b', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| knownFeatures['c'] = ExperimentalFeature( |
| index: 2, |
| enableString: 'c', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'c', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var validationResult = |
| getValidateCombinationResult(['a', 'no-c'], ['no-b', 'c']); |
| expect(validationResult, hasLength(1)); |
| var error = validationResult[0]; |
| expect(error.feature, knownFeatures['c']); |
| expect(error.firstValue, false); |
| } |
| |
| test_validateFlagCombination_enable_then_disable() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| knownFeatures['b'] = ExperimentalFeature( |
| index: 1, |
| enableString: 'b', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'b', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| knownFeatures['c'] = ExperimentalFeature( |
| index: 2, |
| enableString: 'c', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'c', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var validationResult = |
| getValidateCombinationResult(['a', 'c'], ['no-b', 'no-c']); |
| expect(validationResult, hasLength(1)); |
| var error = validationResult[0]; |
| expect(error.feature, knownFeatures['c']); |
| expect(error.firstValue, true); |
| } |
| |
| test_validateFlagCombination_ok() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| knownFeatures['b'] = ExperimentalFeature( |
| index: 1, |
| enableString: 'b', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'b', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| knownFeatures['c'] = ExperimentalFeature( |
| index: 2, |
| enableString: 'c', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'c', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| expect(getValidateCombinationResult(['a', 'c'], ['no-b', 'c']), isEmpty); |
| } |
| |
| test_validateFlags_conflicting_flags_disable_then_enable() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var validationResult = getValidationResult(['no-a', 'a']); |
| expect(validationResult, hasLength(1)); |
| var error = validationResult[0] as ConflictingFlags; |
| expect(error.stringIndex, 1); |
| expect(error.flag, 'a'); |
| expect(error.isError, true); |
| expect(error.feature, knownFeatures['a']); |
| expect(error.previousStringIndex, 0); |
| expect(error.requestedValue, true); |
| } |
| |
| test_validateFlags_conflicting_flags_enable_then_disable() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var validationResult = getValidationResult(['a', 'no-a']); |
| expect(validationResult, hasLength(1)); |
| var error = validationResult[0] as ConflictingFlags; |
| expect(error.stringIndex, 1); |
| expect(error.flag, 'no-a'); |
| expect(error.isError, true); |
| expect(error.feature, knownFeatures['a']); |
| expect(error.previousStringIndex, 0); |
| expect(error.requestedValue, false); |
| } |
| |
| test_validateFlags_ignore_redundant_disable_flags() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| expect(getValidationResult(['no-a', 'no-a']), isEmpty); |
| } |
| |
| test_validateFlags_ignore_redundant_enable_flags() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: false, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| expect(getValidationResult(['a', 'a']), isEmpty); |
| } |
| |
| test_validateFlags_illegal_use_of_expired_flag_disable() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: true, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| var validationResult = getValidationResult(['no-a']); |
| expect(validationResult, hasLength(1)); |
| var error = validationResult[0] as IllegalUseOfExpiredFlag; |
| expect(error.stringIndex, 0); |
| expect(error.flag, 'no-a'); |
| expect(error.isError, true); |
| expect(error.feature, knownFeatures['a']); |
| } |
| |
| test_validateFlags_illegal_use_of_expired_flag_enable() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: true, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var validationResult = getValidationResult(['a']); |
| expect(validationResult, hasLength(1)); |
| var error = validationResult[0] as IllegalUseOfExpiredFlag; |
| expect(error.stringIndex, 0); |
| expect(error.flag, 'a'); |
| expect(error.isError, true); |
| expect(error.feature, knownFeatures['a']); |
| } |
| |
| test_validateFlags_unnecessary_use_of_expired_flag_disable() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: false, |
| isExpired: true, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: null, |
| ); |
| var validationResult = getValidationResult(['no-a']); |
| expect(validationResult, hasLength(1)); |
| var error = validationResult[0] as UnnecessaryUseOfExpiredFlag; |
| expect(error.stringIndex, 0); |
| expect(error.flag, 'no-a'); |
| expect(error.isError, false); |
| expect(error.feature, knownFeatures['a']); |
| } |
| |
| test_validateFlags_unnecessary_use_of_expired_flag_enable() { |
| knownFeatures['a'] = ExperimentalFeature( |
| index: 0, |
| enableString: 'a', |
| isEnabledByDefault: true, |
| isExpired: true, |
| documentation: 'a', |
| experimentalReleaseVersion: null, |
| releaseVersion: Version.parse('1.0.0'), |
| ); |
| var validationResult = getValidationResult(['a']); |
| expect(validationResult, hasLength(1)); |
| var error = validationResult[0] as UnnecessaryUseOfExpiredFlag; |
| expect(error.stringIndex, 0); |
| expect(error.flag, 'a'); |
| expect(error.isError, false); |
| expect(error.feature, knownFeatures['a']); |
| } |
| |
| test_validateFlags_unrecognized_flag() { |
| var validationResult = getValidationResult(['a']); |
| expect(validationResult, hasLength(1)); |
| var error = validationResult[0] as UnrecognizedFlag; |
| expect(error.stringIndex, 0); |
| expect(error.flag, 'a'); |
| expect(error.isError, true); |
| } |
| } |