diff --git a/.packages b/.packages
index c5944a1..db0e7d7 100644
--- a/.packages
+++ b/.packages
@@ -59,6 +59,7 @@
 meta:pkg/meta/lib
 mime:third_party/pkg/mime/lib
 mockito:third_party/pkg/mockito/lib
+modular_test:pkg/modular_test/lib
 mustache:third_party/pkg/mustache/lib
 oauth2:third_party/pkg/oauth2/lib
 observatory:runtime/observatory/lib
diff --git a/pkg/modular_test/lib/src/io_pipeline.dart b/pkg/modular_test/lib/src/io_pipeline.dart
new file mode 100644
index 0000000..a92c6c7
--- /dev/null
+++ b/pkg/modular_test/lib/src/io_pipeline.dart
@@ -0,0 +1,91 @@
+// Copyright (c) 2019, 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.
+
+/// An implementation of [Pipeline] that runs using IO.
+///
+/// To define a step, implement [IOModularStep].
+import 'dart:io';
+
+import 'pipeline.dart';
+import 'suite.dart';
+
+/// Indicates where to read and write data produced by the pipeline.
+typedef ModuleDataToRelativeUri = Uri Function(Module, DataId);
+
+abstract class IOModularStep extends ModularStep {
+  /// Execute the step under [root].
+  ///
+  /// The [root] folder will hold all inputs and will be used to emit the output
+  /// of this step.
+  ///
+  /// Assets created on previous steps of the pipeline should be available under
+  /// `root.resolveUri(toUri(module, dataId))` and the output of this step
+  /// should be stored under `root.resolveUri(toUri(module, resultKind))`.
+  Future<void> execute(Module module, Uri root, ModuleDataToRelativeUri toUri);
+}
+
+class IOPipeline extends Pipeline<IOModularStep> {
+  /// A folder per step. The key is the data id produced by a specific step.
+  ///
+  /// This contains internal state used during the run of the pipeline, but is
+  /// expected to be null before and after the pipeline is executed.
+  Map<DataId, Uri> _tmpFolders;
+  Map<DataId, Uri> get tmpFoldersForTesting => _tmpFolders;
+  bool saveFoldersForTesting;
+
+  IOPipeline(List<ModularStep> steps, {this.saveFoldersForTesting: false})
+      : super(steps);
+
+  @override
+  Future<void> run(ModularTest test) async {
+    assert(_tmpFolders == null);
+    _tmpFolders = {};
+    await super.run(test);
+    if (!saveFoldersForTesting) {
+      for (var folder in _tmpFolders.values) {
+        await Directory.fromUri(folder).delete(recursive: true);
+      }
+      _tmpFolders = null;
+    }
+  }
+
+  @override
+  Future<void> runStep(IOModularStep step, Module module,
+      Map<Module, Set<DataId>> visibleData) async {
+    var folder = await Directory.systemTemp
+        .createTemp('modular_test_${step.resultKind}-');
+    _tmpFolders[step.resultKind] ??= (await Directory.systemTemp
+            .createTemp('modular_test_${step.resultKind}_res-'))
+        .uri;
+    for (var module in visibleData.keys) {
+      for (var dataId in visibleData[module]) {
+        var filename = "${module.name}.${dataId.name}";
+        var assetUri = _tmpFolders[dataId].resolve(filename);
+        await File.fromUri(assetUri)
+            .copy(folder.uri.resolve(filename).toFilePath());
+      }
+    }
+    if (step.needsSources) {
+      for (var uri in module.sources) {
+        var originalUri = module.rootUri.resolveUri(uri);
+        await File.fromUri(originalUri)
+            .copy(folder.uri.resolveUri(uri).toFilePath());
+      }
+    }
+
+    await step.execute(module, folder.uri,
+        (Module m, DataId id) => Uri.parse("${m.name}.${id.name}"));
+
+    var outputFile = File.fromUri(
+        folder.uri.resolve("${module.name}.${step.resultKind.name}"));
+    if (!await outputFile.exists()) {
+      throw StateError(
+          "Step '${step.runtimeType}' didn't produce an output file");
+    }
+    await outputFile.copy(_tmpFolders[step.resultKind]
+        .resolve("${module.name}.${step.resultKind.name}")
+        .toFilePath());
+    await folder.delete(recursive: true);
+  }
+}
diff --git a/pkg/modular_test/lib/src/memory_pipeline.dart b/pkg/modular_test/lib/src/memory_pipeline.dart
new file mode 100644
index 0000000..4254bbc
--- /dev/null
+++ b/pkg/modular_test/lib/src/memory_pipeline.dart
@@ -0,0 +1,62 @@
+// Copyright (c) 2019, 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.
+
+/// An implementation of [Pipeline] that runs in-memory.
+///
+/// To define a step, implement [MemoryModularStep].
+import 'pipeline.dart';
+import 'suite.dart';
+
+/// A hook to fetch data previously computed for a dependency.
+typedef ModuleDataProvider = Object Function(Module, DataId);
+typedef SourceProvider = String Function(Uri);
+
+abstract class MemoryModularStep extends ModularStep {
+  Future<Object> execute(Module module, SourceProvider sourceProvider,
+      ModuleDataProvider dataProvider);
+}
+
+class MemoryPipeline extends Pipeline<MemoryModularStep> {
+  final Map<Uri, String> _sources;
+
+  /// Internal state to hold the current results as they are computed by the
+  /// pipeline. Expected to be null before and after the pipeline runs.
+  Map<Module, Map<DataId, Object>> _results;
+
+  /// A copy of [_result] at the time the pipeline last finished running.
+  Map<Module, Map<DataId, Object>> resultsForTesting;
+
+  MemoryPipeline(this._sources, List<ModularStep> steps) : super(steps);
+
+  @override
+  Future<void> run(ModularTest test) async {
+    assert(_results == null);
+    _results = {};
+    await super.run(test);
+    resultsForTesting = _results;
+    _results = null;
+  }
+
+  @override
+  Future<void> runStep(MemoryModularStep step, Module module,
+      Map<Module, Set<DataId>> visibleData) async {
+    Map<Module, Map<DataId, Object>> inputData = {};
+    visibleData.forEach((module, dataIdSet) {
+      inputData[module] = {};
+      for (var dataId in dataIdSet) {
+        inputData[module][dataId] = _results[module][dataId];
+      }
+    });
+    Map<Uri, String> inputSources = {};
+    if (step.needsSources) {
+      module.sources.forEach((relativeUri) {
+        var uri = module.rootUri.resolveUri(relativeUri);
+        inputSources[uri] = _sources[uri];
+      });
+    }
+    Object result = await step.execute(module, (Uri uri) => inputSources[uri],
+        (Module m, DataId id) => inputData[m][id]);
+    (_results[module] ??= {})[step.resultKind] = result;
+  }
+}
diff --git a/pkg/modular_test/lib/src/pipeline.dart b/pkg/modular_test/lib/src/pipeline.dart
new file mode 100644
index 0000000..1323459
--- /dev/null
+++ b/pkg/modular_test/lib/src/pipeline.dart
@@ -0,0 +1,153 @@
+// Copyright (c) 2019, 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.
+
+/// Abstraction for a compilation pipeline.
+///
+/// A pipeline defines how modular steps are excuted and ensures that a step
+/// only has access to the data it declares.
+///
+/// The abstract implementation validates how the data is declared, and the
+/// underlying implementations enforce the access to data in different ways.
+///
+/// The IO-based implementation ensures hermeticity by copying data to different
+/// directories. The memory-based implementation ensures hemeticity by filtering
+/// out the data before invoking the next step.
+import 'suite.dart';
+
+/// Describes a step in a modular compilation pipeline.
+class ModularStep {
+  /// Whether this step needs to read the source files in the module.
+  final bool needsSources;
+
+  /// Data that this step needs to read about dependencies.
+  ///
+  /// This can be data produced on a previous stage of the pipeline
+  /// or produced by this same step when it was run on a dependency.
+  ///
+  /// If this list includes [resultKind], then the modular-step has to be run on
+  /// dependencies before it is run on a module. Otherwise, it could be run in
+  /// parallel.
+  final List<DataId> dependencyDataNeeded;
+
+  /// Data that this step needs to read about the module itself.
+  ///
+  /// This is meant to be data produced in earlier stages of the modular
+  /// pipeline. It is an error to include [resultKind] in this list.
+  final List<DataId> moduleDataNeeded;
+
+  /// Data that this step produces.
+  final DataId resultKind;
+
+  ModularStep(
+      {this.needsSources: true,
+      this.dependencyDataNeeded: const [],
+      this.moduleDataNeeded: const [],
+      this.resultKind});
+}
+
+/// An object to uniquely identify modular data produced by a modular step.
+///
+/// Two modular steps on the same pipeline cannot emit the same data.
+class DataId {
+  final String name;
+
+  const DataId(this.name);
+
+  @override
+  String toString() => name;
+}
+
+abstract class Pipeline<S extends ModularStep> {
+  final List<S> steps;
+
+  Pipeline(this.steps) {
+    _validate();
+  }
+
+  void _validate() {
+    // Ensure that steps consume only data that was produced by previous steps
+    // or by the same step on a dependency.
+    Map<DataId, S> previousKinds = {};
+    for (var step in steps) {
+      var resultKind = step.resultKind;
+      if (previousKinds.containsKey(resultKind)) {
+        _validationError("Cannot produce the same data on two modular steps."
+            " '$resultKind' was previously produced by "
+            "'${previousKinds[resultKind].runtimeType}' but "
+            "'${step.runtimeType}' also produces the same data.");
+      }
+      previousKinds[resultKind] = step;
+      for (var dataId in step.dependencyDataNeeded) {
+        if (!previousKinds.containsKey(dataId)) {
+          _validationError(
+              "Step '${step.runtimeType}' needs data '${dataId}', but the data"
+              " is not produced by this or a preceding step.");
+        }
+      }
+      for (var dataId in step.moduleDataNeeded) {
+        if (!previousKinds.containsKey(dataId)) {
+          _validationError(
+              "Step '${step.runtimeType}' needs data '${dataId}', but the data"
+              " is not produced by a preceding step.");
+        }
+        if (dataId == resultKind) {
+          _validationError(
+              "Circular dependency on '$dataId' in step '${step.runtimeType}'");
+        }
+      }
+    }
+  }
+
+  void _validationError(String s) => throw InvalidPipelineError(s);
+
+  Future<void> run(ModularTest test) async {
+    // TODO(sigmund): validate that [ModularTest] has no cycles.
+    Map<Module, Set<DataId>> computedData = {};
+    for (var step in steps) {
+      await _recursiveRun(step, test.mainModule, computedData, {});
+    }
+  }
+
+  Future<void> _recursiveRun(S step, Module module,
+      Map<Module, Set<DataId>> computedData, Set<Module> seen) async {
+    if (!seen.add(module)) return;
+    for (var dependency in module.dependencies) {
+      await _recursiveRun(step, dependency, computedData, seen);
+    }
+    // Include only requested data from transitive dependencies.
+    Map<Module, Set<DataId>> visibleData = {};
+
+    // TODO(sigmund): consider excluding parent modules here. In particular,
+    // [seen] not only contains transitive dependencies, but also this module
+    // and parent modules. Technically we haven't computed any data for those,
+    // so we shouldn't be including any entries for parent modules in
+    // [visibleData].
+    seen.forEach((dep) {
+      if (dep == module) return;
+      visibleData[dep] = {};
+      for (var dataId in step.dependencyDataNeeded) {
+        if (computedData[dep].contains(dataId)) {
+          visibleData[dep].add(dataId);
+        }
+      }
+    });
+    visibleData[module] = {};
+    for (var dataId in step.moduleDataNeeded) {
+      if (computedData[module].contains(dataId)) {
+        visibleData[module].add(dataId);
+      }
+    }
+    await runStep(step, module, visibleData);
+    (computedData[module] ??= {}).add(step.resultKind);
+  }
+
+  Future<void> runStep(
+      S step, Module module, Map<Module, Set<DataId>> visibleData);
+}
+
+class InvalidPipelineError extends Error {
+  final String message;
+  InvalidPipelineError(this.message);
+  String toString() => "Invalid pipeline: $message";
+}
diff --git a/pkg/modular_test/lib/src/suite.dart b/pkg/modular_test/lib/src/suite.dart
new file mode 100644
index 0000000..bba158e
--- /dev/null
+++ b/pkg/modular_test/lib/src/suite.dart
@@ -0,0 +1,51 @@
+// Copyright (c) 2019, 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.
+
+/// Model for a modular test.
+
+/// A modular test declares the structure of the test code: what files are
+/// grouped as a module and how modules depend on one another.
+class ModularTest {
+  /// Modules that will be compiled by for modular test
+  final List<Module> modules;
+
+  /// The module containing the main entry method.
+  final Module mainModule;
+
+  ModularTest(this.modules, this.mainModule)
+      : assert(mainModule != null && modules.length > 0);
+}
+
+/// A single module in a modular test.
+class Module {
+  /// A short name to identify this module.
+  final String name;
+
+  /// Other modules that need to be compiled first and whose result may be
+  /// necessary in order to compile this module.
+  final List<Module> dependencies;
+
+  /// Root under which all sources in the module can be found.
+  final Uri rootUri;
+
+  /// Source files that are part of this module only. Stored as a relative [Uri]
+  /// from [rootUri].
+  final List<Uri> sources;
+
+  /// The file containing the main entry method, if any. Stored as a relative
+  /// [Uri] from [rootUri].
+  final Uri mainSource;
+
+  Module(this.name, this.dependencies, this.rootUri, this.sources,
+      this.mainSource) {
+    if (!_validModuleName.hasMatch(name)) {
+      throw "invalid module name: $name";
+    }
+  }
+
+  @override
+  String toString() => '[module $name]';
+}
+
+final RegExp _validModuleName = new RegExp(r'^[a-zA-Z_][a-zA-Z0-9_]*$');
diff --git a/pkg/modular_test/pubspec.yaml b/pkg/modular_test/pubspec.yaml
new file mode 100644
index 0000000..94f26d8
--- /dev/null
+++ b/pkg/modular_test/pubspec.yaml
@@ -0,0 +1,14 @@
+name: modular_test
+publish_to: none
+description: >
+ Small framework to test modular pipelines.
+ This is used within the Dart SDK to define and validate modular tests, and to
+ execute them using the modular pipeline of different SDK tools.
+environment:
+  sdk: ">=2.2.1 <3.0.0"
+
+dependencies:
+  yaml: ^2.1.15
+
+dev_dependencies:
+  test: any
diff --git a/pkg/modular_test/test/io_pipeline_test.dart b/pkg/modular_test/test/io_pipeline_test.dart
new file mode 100644
index 0000000..a30207c
--- /dev/null
+++ b/pkg/modular_test/test/io_pipeline_test.dart
@@ -0,0 +1,180 @@
+// Copyright (c) 2019, 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.
+
+/// Unit test for in-memory pipelines.
+import 'dart:io';
+
+import 'package:modular_test/src/io_pipeline.dart';
+
+import 'pipeline_common.dart';
+
+main() async {
+  var uri = Directory.systemTemp.uri.resolve("io_modular_test_root/");
+  int i = 0;
+  while (await Directory.fromUri(uri).exists()) {
+    uri = Directory.systemTemp.uri.resolve("io_modular_test_root$i/");
+    i++;
+  }
+  runPipelineTest(new IOPipelineTestStrategy(uri));
+}
+
+/// The strategy implementation to exercise the pipeline test on a
+/// [IOPipeline].
+class IOPipelineTestStrategy implements PipelineTestStrategy<IOModularStep> {
+  @override
+  final Uri testRootUri;
+
+  IOPipelineTestStrategy(this.testRootUri);
+
+  @override
+  Future<Pipeline<IOModularStep>> createPipeline(
+      Map<Uri, String> sources, List<IOModularStep> steps) async {
+    await Directory.fromUri(testRootUri).create();
+    for (var uri in sources.keys) {
+      var file = new File.fromUri(uri);
+      await file.create(recursive: true);
+      await file.writeAsStringSync(sources[uri]);
+    }
+    return new IOPipeline(steps, saveFoldersForTesting: true);
+  }
+
+  @override
+  IOModularStep createConcatStep({bool requestSources: true}) =>
+      ConcatStep(requestSources);
+
+  @override
+  IOModularStep createLowerCaseStep({bool requestModuleData: true}) =>
+      LowerCaseStep(requestModuleData);
+
+  @override
+  IOModularStep createReplaceAndJoinStep(
+          {bool requestDependenciesData: true}) =>
+      ReplaceAndJoinStep(requestDependenciesData);
+
+  @override
+  IOModularStep createReplaceAndJoinStep2(
+          {bool requestDependenciesData: true}) =>
+      ReplaceAndJoinStep2(requestDependenciesData);
+
+  @override
+  String getResult(covariant IOPipeline pipeline, Module m, DataId dataId) {
+    var folderUri = pipeline.tmpFoldersForTesting[dataId];
+    return File.fromUri(folderUri.resolve("${m.name}.${dataId.name}"))
+        .readAsStringSync();
+  }
+
+  @override
+  Future<void> cleanup(Pipeline<IOModularStep> pipeline) async {
+    var folders = (pipeline as IOPipeline).tmpFoldersForTesting.values;
+    for (var folder in folders) {
+      await Directory.fromUri(folder).delete(recursive: true);
+    }
+    await Directory.fromUri(testRootUri).delete(recursive: true);
+  }
+}
+
+class ConcatStep implements IOModularStep {
+  final bool needsSources;
+  List<DataId> get dependencyDataNeeded => const [];
+  List<DataId> get moduleDataNeeded => const [];
+  DataId get resultKind => const DataId("concat");
+
+  ConcatStep(this.needsSources);
+
+  @override
+  Future<void> execute(
+      Module module, Uri root, ModuleDataToRelativeUri toUri) async {
+    var buffer = new StringBuffer();
+    for (var uri in module.sources) {
+      var file = File.fromUri(root.resolveUri(uri));
+      String data = await file.exists() ? await file.readAsString() : null;
+      buffer.write("$uri: ${data}\n");
+    }
+    await File.fromUri(root.resolveUri(toUri(module, resultKind)))
+        .writeAsString('$buffer');
+  }
+}
+
+Future<String> _readHelper(Module module, Uri root, DataId dataId,
+    ModuleDataToRelativeUri toUri) async {
+  var file = File.fromUri(root.resolveUri(toUri(module, dataId)));
+  if (await file.exists()) {
+    return await file.readAsString();
+  }
+  return null;
+}
+
+class LowerCaseStep implements IOModularStep {
+  bool get needsSources => false;
+  List<DataId> get dependencyDataNeeded => const [];
+  final List<DataId> moduleDataNeeded;
+  DataId get resultKind => const DataId("lowercase");
+
+  LowerCaseStep(bool requestConcat)
+      : moduleDataNeeded = requestConcat ? const [DataId("concat")] : const [];
+
+  @override
+  Future<void> execute(
+      Module module, Uri root, ModuleDataToRelativeUri toUri) async {
+    var concatData =
+        await _readHelper(module, root, const DataId("concat"), toUri);
+    if (concatData == null) concatData = "data for $module was null";
+    await File.fromUri(root.resolveUri(toUri(module, resultKind)))
+        .writeAsString(concatData.toLowerCase());
+  }
+}
+
+class ReplaceAndJoinStep implements IOModularStep {
+  bool get needsSources => false;
+  final List<DataId> dependencyDataNeeded;
+  List<DataId> get moduleDataNeeded => const [DataId("lowercase")];
+  DataId get resultKind => const DataId("join");
+
+  ReplaceAndJoinStep(bool requestDependencies)
+      : dependencyDataNeeded =
+            requestDependencies ? const [DataId("join")] : [];
+
+  @override
+  Future<void> execute(
+      Module module, Uri root, ModuleDataToRelativeUri toUri) async {
+    var buffer = new StringBuffer();
+    for (var dependency in module.dependencies) {
+      var depData =
+          await _readHelper(dependency, root, const DataId("join"), toUri);
+      buffer.write("$depData\n");
+    }
+    var moduleData =
+        await _readHelper(module, root, const DataId("lowercase"), toUri);
+    buffer.write(moduleData.replaceAll(".dart:", ""));
+    await File.fromUri(root.resolveUri(toUri(module, resultKind)))
+        .writeAsString('$buffer');
+  }
+}
+
+class ReplaceAndJoinStep2 implements IOModularStep {
+  bool get needsSources => false;
+  final List<DataId> dependencyDataNeeded;
+  List<DataId> get moduleDataNeeded => const [DataId("lowercase")];
+  DataId get resultKind => const DataId("join");
+
+  ReplaceAndJoinStep2(bool requestDependencies)
+      : dependencyDataNeeded =
+            requestDependencies ? const [DataId("lowercase")] : [];
+
+  @override
+  Future<void> execute(
+      Module module, Uri root, ModuleDataToRelativeUri toUri) async {
+    var buffer = new StringBuffer();
+    for (var dependency in module.dependencies) {
+      var depData =
+          await _readHelper(dependency, root, const DataId("lowercase"), toUri);
+      buffer.write("$depData\n");
+    }
+    var moduleData =
+        await _readHelper(module, root, const DataId("lowercase"), toUri);
+    buffer.write(moduleData.replaceAll(".dart:", ""));
+    await File.fromUri(root.resolveUri(toUri(module, resultKind)))
+        .writeAsString('$buffer');
+  }
+}
diff --git a/pkg/modular_test/test/memory_pipeline_test.dart b/pkg/modular_test/test/memory_pipeline_test.dart
new file mode 100644
index 0000000..29c407f
--- /dev/null
+++ b/pkg/modular_test/test/memory_pipeline_test.dart
@@ -0,0 +1,132 @@
+// Copyright (c) 2019, 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.
+
+/// Unit test for in-memory pipelines.
+import 'dart:async';
+
+import 'package:modular_test/src/memory_pipeline.dart';
+
+import 'pipeline_common.dart';
+
+main() {
+  runPipelineTest(new MemoryPipelineTestStrategy());
+}
+
+/// The strategy implementation to exercise the pipeline test on a
+/// [MemoryPipeline].
+class MemoryPipelineTestStrategy
+    implements PipelineTestStrategy<MemoryModularStep> {
+  @override
+  Uri get testRootUri => Uri.parse('/');
+
+  @override
+  FutureOr<Pipeline<MemoryModularStep>> createPipeline(
+      Map<Uri, String> sources, List<MemoryModularStep> steps) {
+    return new MemoryPipeline(sources, steps);
+  }
+
+  @override
+  MemoryModularStep createConcatStep({bool requestSources: true}) =>
+      ConcatStep(requestSources);
+
+  @override
+  MemoryModularStep createLowerCaseStep({bool requestModuleData: true}) =>
+      LowerCaseStep(requestModuleData);
+
+  @override
+  MemoryModularStep createReplaceAndJoinStep(
+          {bool requestDependenciesData: true}) =>
+      ReplaceAndJoinStep(requestDependenciesData);
+
+  @override
+  MemoryModularStep createReplaceAndJoinStep2(
+          {bool requestDependenciesData: true}) =>
+      ReplaceAndJoinStep2(requestDependenciesData);
+
+  @override
+  String getResult(covariant MemoryPipeline pipeline, Module m, DataId dataId) {
+    return pipeline.resultsForTesting[m][dataId];
+  }
+
+  FutureOr<void> cleanup(Pipeline<MemoryModularStep> pipeline) => null;
+}
+
+class ConcatStep implements MemoryModularStep {
+  final bool needsSources;
+  List<DataId> get dependencyDataNeeded => const [];
+  List<DataId> get moduleDataNeeded => const [];
+  DataId get resultKind => const DataId("concat");
+
+  ConcatStep(this.needsSources);
+
+  Future<Object> execute(Module module, SourceProvider sourceProvider,
+      ModuleDataProvider dataProvider) {
+    var buffer = new StringBuffer();
+    for (var uri in module.sources) {
+      buffer.write("$uri: ${sourceProvider(module.rootUri.resolveUri(uri))}\n");
+    }
+    return Future.value('$buffer');
+  }
+}
+
+class LowerCaseStep implements MemoryModularStep {
+  bool get needsSources => false;
+  List<DataId> get dependencyDataNeeded => const [];
+  final List<DataId> moduleDataNeeded;
+  DataId get resultKind => const DataId("lowercase");
+
+  LowerCaseStep(bool requestConcat)
+      : moduleDataNeeded = requestConcat ? const [DataId("concat")] : const [];
+
+  Future<Object> execute(Module module, SourceProvider sourceProvider,
+      ModuleDataProvider dataProvider) {
+    var concatData = dataProvider(module, const DataId("concat")) as String;
+    if (concatData == null) return Future.value("data for $module was null");
+    return Future.value(concatData.toLowerCase());
+  }
+}
+
+class ReplaceAndJoinStep implements MemoryModularStep {
+  bool get needsSources => false;
+  final List<DataId> dependencyDataNeeded;
+  List<DataId> get moduleDataNeeded => const [DataId("lowercase")];
+  DataId get resultKind => const DataId("join");
+
+  ReplaceAndJoinStep(bool requestDependencies)
+      : dependencyDataNeeded =
+            requestDependencies ? const [DataId("join")] : [];
+
+  Future<Object> execute(Module module, SourceProvider sourceProvider,
+      ModuleDataProvider dataProvider) {
+    var buffer = new StringBuffer();
+    for (var dependency in module.dependencies) {
+      buffer.write("${dataProvider(dependency, const DataId("join"))}\n");
+    }
+    var moduleData = dataProvider(module, const DataId("lowercase")) as String;
+    buffer.write(moduleData.replaceAll(".dart:", ""));
+    return Future.value('$buffer');
+  }
+}
+
+class ReplaceAndJoinStep2 implements MemoryModularStep {
+  bool get needsSources => false;
+  final List<DataId> dependencyDataNeeded;
+  List<DataId> get moduleDataNeeded => const [DataId("lowercase")];
+  DataId get resultKind => const DataId("join");
+
+  ReplaceAndJoinStep2(bool requestDependencies)
+      : dependencyDataNeeded =
+            requestDependencies ? const [DataId("lowercase")] : [];
+
+  Future<Object> execute(Module module, SourceProvider sourceProvider,
+      ModuleDataProvider dataProvider) {
+    var buffer = new StringBuffer();
+    for (var dependency in module.dependencies) {
+      buffer.write("${dataProvider(dependency, const DataId("lowercase"))}\n");
+    }
+    var moduleData = dataProvider(module, const DataId("lowercase")) as String;
+    buffer.write(moduleData.replaceAll(".dart:", ""));
+    return Future.value('$buffer');
+  }
+}
diff --git a/pkg/modular_test/test/pipeline_common.dart b/pkg/modular_test/test/pipeline_common.dart
new file mode 100644
index 0000000..159e464
--- /dev/null
+++ b/pkg/modular_test/test/pipeline_common.dart
@@ -0,0 +1,192 @@
+// Copyright (c) 2019, 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.
+
+/// Defines the abstract skeleton of the memory and io pipeline tests.
+///
+/// The idea is to ensure that pipelines are evaluated in the expected order
+/// and that steps are hermetic in that they are only provided the data they
+/// request.
+///
+/// We place most of the logic here to guarantee that the two different pipeline
+/// implementations are consistent with each other.
+import 'dart:async';
+
+import 'package:test/test.dart';
+import 'package:modular_test/src/suite.dart';
+import 'package:modular_test/src/pipeline.dart';
+
+export 'package:modular_test/src/suite.dart';
+export 'package:modular_test/src/pipeline.dart';
+
+/// A strategy to create the steps and pipelines used by the pipeline test. This
+/// is implemented in `memory_pipeline_test.dart` and `io_pipeline_test.dart`.
+abstract class PipelineTestStrategy<S extends ModularStep> {
+  /// Root URI where test sources are found.
+  Uri get testRootUri;
+
+  /// Creates a pipeline with the given sources and steps. Steps will be created
+  /// by other methods in this strategy to ensure they are compatible with to
+  /// the pipeline created here.
+  FutureOr<Pipeline<S>> createPipeline(Map<Uri, String> sources, List<S> steps);
+
+  /// Create a step that concatenates all contents of the sources in a module.
+  S createConcatStep({bool requestSources: true});
+
+  /// Create a step that consumes the concat step result and converts the
+  /// contents to lower-case.
+  S createLowerCaseStep({bool requestModuleData: true});
+
+  /// Create a step that consumes the concat and lower-case steps and does a
+  /// replace and join operation as expected in the tests below.
+  ///
+  /// This step consumes it's own data from dependencies.
+  S createReplaceAndJoinStep({bool requestDependenciesData: true});
+
+  /// Create a step that consumes the concat and lower-case steps and does a
+  /// replace and join operation as expected in the tests below.
+  ///
+  /// This step consumes the lower-case step data from dependencies.
+  S createReplaceAndJoinStep2({bool requestDependenciesData: true});
+
+  /// Return the result data produced by a modular step.
+  String getResult(Pipeline<S> pipeline, Module m, DataId dataId);
+
+  /// Do any cleanup work needed after pipeline is completed. Needed because
+  /// some implementations retain data around to be able to answer [getResult]
+  /// queries.
+  FutureOr<void> cleanup(Pipeline<S> pipeline);
+}
+
+runPipelineTest<S extends ModularStep>(PipelineTestStrategy<S> testStrategy) {
+  var sources = {
+    testStrategy.testRootUri.resolve("a1.dart"): 'A1',
+    testStrategy.testRootUri.resolve("a2.dart"): 'A2',
+    testStrategy.testRootUri.resolve("b/b1.dart"): 'B1',
+    testStrategy.testRootUri.resolve("b/b2.dart"): 'B2',
+  };
+
+  var m1 = Module("a", const [], testStrategy.testRootUri,
+      [Uri.parse("a1.dart"), Uri.parse("a2.dart")], null);
+  var m2 = Module("b", [m1], testStrategy.testRootUri.resolve('b/'),
+      [Uri.parse("b1.dart"), Uri.parse("b2.dart")], null);
+
+  var singleModuleInput = ModularTest([m1], m1);
+  var multipleModulesInput = ModularTest([m1, m2], m2);
+
+  test('can read source data if requested', () async {
+    var concatStep = testStrategy.createConcatStep();
+    var pipeline = await testStrategy.createPipeline(sources, <S>[concatStep]);
+    await pipeline.run(singleModuleInput);
+    expect(testStrategy.getResult(pipeline, m1, concatStep.resultKind),
+        "a1.dart: A1\na2.dart: A2\n");
+    await testStrategy.cleanup(pipeline);
+  });
+
+  test('cannot read source data if not requested', () async {
+    var concatStep = testStrategy.createConcatStep(requestSources: false);
+    var pipeline = await testStrategy.createPipeline(sources, <S>[concatStep]);
+    await pipeline.run(singleModuleInput);
+    expect(testStrategy.getResult(pipeline, m1, concatStep.resultKind),
+        "a1.dart: null\na2.dart: null\n");
+    await testStrategy.cleanup(pipeline);
+  });
+
+  test('step is applied to all modules', () async {
+    var concatStep = testStrategy.createConcatStep();
+    var pipeline = await testStrategy.createPipeline(sources, <S>[concatStep]);
+    await pipeline.run(multipleModulesInput);
+    expect(testStrategy.getResult(pipeline, m1, concatStep.resultKind),
+        "a1.dart: A1\na2.dart: A2\n");
+    expect(testStrategy.getResult(pipeline, m2, concatStep.resultKind),
+        "b1.dart: B1\nb2.dart: B2\n");
+    await testStrategy.cleanup(pipeline);
+  });
+
+  test('can read previous step results if requested', () async {
+    var concatStep = testStrategy.createConcatStep();
+    var lowercaseStep = testStrategy.createLowerCaseStep();
+    var pipeline = await testStrategy
+        .createPipeline(sources, <S>[concatStep, lowercaseStep]);
+    await pipeline.run(multipleModulesInput);
+    expect(testStrategy.getResult(pipeline, m1, lowercaseStep.resultKind),
+        "a1.dart: a1\na2.dart: a2\n");
+    expect(testStrategy.getResult(pipeline, m2, lowercaseStep.resultKind),
+        "b1.dart: b1\nb2.dart: b2\n");
+    await testStrategy.cleanup(pipeline);
+  });
+
+  test('cannot read previous step results if not requested', () async {
+    var concatStep = testStrategy.createConcatStep();
+    var lowercaseStep =
+        testStrategy.createLowerCaseStep(requestModuleData: false);
+    var pipeline = await testStrategy
+        .createPipeline(sources, <S>[concatStep, lowercaseStep]);
+    await pipeline.run(multipleModulesInput);
+    expect(testStrategy.getResult(pipeline, m1, lowercaseStep.resultKind),
+        "data for [module a] was null");
+    expect(testStrategy.getResult(pipeline, m2, lowercaseStep.resultKind),
+        "data for [module b] was null");
+    await testStrategy.cleanup(pipeline);
+  });
+
+  test('can read same-step results of dependencies if requested', () async {
+    var concatStep = testStrategy.createConcatStep();
+    var lowercaseStep = testStrategy.createLowerCaseStep();
+    var replaceJoinStep = testStrategy.createReplaceAndJoinStep();
+    var pipeline = await testStrategy.createPipeline(
+        sources, <S>[concatStep, lowercaseStep, replaceJoinStep]);
+    await pipeline.run(multipleModulesInput);
+    expect(testStrategy.getResult(pipeline, m1, replaceJoinStep.resultKind),
+        "a1 a1\na2 a2\n");
+    expect(testStrategy.getResult(pipeline, m2, replaceJoinStep.resultKind),
+        "a1 a1\na2 a2\n\nb1 b1\nb2 b2\n");
+    await testStrategy.cleanup(pipeline);
+  });
+
+  test('cannot read same-step results of dependencies if not requested',
+      () async {
+    var concatStep = testStrategy.createConcatStep();
+    var lowercaseStep = testStrategy.createLowerCaseStep();
+    var replaceJoinStep =
+        testStrategy.createReplaceAndJoinStep(requestDependenciesData: false);
+    var pipeline = await testStrategy.createPipeline(
+        sources, <S>[concatStep, lowercaseStep, replaceJoinStep]);
+    await pipeline.run(multipleModulesInput);
+    expect(testStrategy.getResult(pipeline, m1, replaceJoinStep.resultKind),
+        "a1 a1\na2 a2\n");
+    expect(testStrategy.getResult(pipeline, m2, replaceJoinStep.resultKind),
+        "null\nb1 b1\nb2 b2\n");
+    await testStrategy.cleanup(pipeline);
+  });
+
+  test('can read prior step results of dependencies if requested', () async {
+    var concatStep = testStrategy.createConcatStep();
+    var lowercaseStep = testStrategy.createLowerCaseStep();
+    var replaceJoinStep = testStrategy.createReplaceAndJoinStep2();
+    var pipeline = await testStrategy.createPipeline(
+        sources, <S>[concatStep, lowercaseStep, replaceJoinStep]);
+    await pipeline.run(multipleModulesInput);
+    expect(testStrategy.getResult(pipeline, m1, replaceJoinStep.resultKind),
+        "a1 a1\na2 a2\n");
+    expect(testStrategy.getResult(pipeline, m2, replaceJoinStep.resultKind),
+        "a1.dart: a1\na2.dart: a2\n\nb1 b1\nb2 b2\n");
+    await testStrategy.cleanup(pipeline);
+  });
+
+  test('cannot read prior step results of dependencies if not requested',
+      () async {
+    var concatStep = testStrategy.createConcatStep();
+    var lowercaseStep = testStrategy.createLowerCaseStep();
+    var replaceJoinStep =
+        testStrategy.createReplaceAndJoinStep2(requestDependenciesData: false);
+    var pipeline = await testStrategy.createPipeline(
+        sources, <S>[concatStep, lowercaseStep, replaceJoinStep]);
+    await pipeline.run(multipleModulesInput);
+    expect(testStrategy.getResult(pipeline, m1, replaceJoinStep.resultKind),
+        "a1 a1\na2 a2\n");
+    expect(testStrategy.getResult(pipeline, m2, replaceJoinStep.resultKind),
+        "null\nb1 b1\nb2 b2\n");
+    await testStrategy.cleanup(pipeline);
+  });
+}
diff --git a/pkg/modular_test/test/validate_test.dart b/pkg/modular_test/test/validate_test.dart
new file mode 100644
index 0000000..6858544
--- /dev/null
+++ b/pkg/modular_test/test/validate_test.dart
@@ -0,0 +1,80 @@
+// Copyright (c) 2019, 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.
+
+/// Unit test for validation of modular steps in a pipeline.
+import 'package:test/test.dart';
+import 'package:modular_test/src/suite.dart';
+import 'package:modular_test/src/pipeline.dart';
+
+main() {
+  test('no steps is OK', () {
+    validateSteps([]);
+  });
+
+  test('no errors', () {
+    var id1 = DataId("data_a");
+    var id2 = DataId("data_b");
+    var id3 = DataId("data_c");
+    validateSteps([
+      ModularStep(
+          needsSources: true, dependencyDataNeeded: [id1], resultKind: id1),
+      ModularStep(moduleDataNeeded: [id1], resultKind: id2),
+      ModularStep(
+          moduleDataNeeded: [id2],
+          dependencyDataNeeded: [id1, id3],
+          resultKind: id3),
+    ]);
+  });
+
+  test('circular dependency is not allowed', () {
+    var id1 = DataId("data_a");
+    expect(
+        () => validateSteps([
+              ModularStep(moduleDataNeeded: [id1], resultKind: id1),
+            ]),
+        throwsA(TypeMatcher<InvalidPipelineError>()));
+  });
+
+  test('out of order dependencies are not allowed', () {
+    var id1 = DataId("data_a");
+    var id2 = DataId("data_b");
+    validateSteps([
+      ModularStep(
+          resultKind: id1), // id1 must be produced before it is consumed.
+      ModularStep(dependencyDataNeeded: [id1], resultKind: id2),
+    ]);
+
+    expect(
+        () => validateSteps([
+              ModularStep(dependencyDataNeeded: [id1], resultKind: id2),
+              ModularStep(resultKind: id1),
+            ]),
+        throwsA(TypeMatcher<InvalidPipelineError>()));
+  });
+
+  test('same data cannot be produced by two steps', () {
+    var id1 = DataId("data_a");
+    expect(
+        () => validateSteps([
+              ModularStep(resultKind: id1),
+              ModularStep(resultKind: id1),
+            ]),
+        throwsA(TypeMatcher<InvalidPipelineError>()));
+  });
+}
+
+validateSteps(List<ModularStep> steps) {
+  new _NoopPipeline(steps);
+}
+
+/// An implementation of [Pipeline] that simply validates the steps, but doesn't
+/// do anything else.
+class _NoopPipeline extends Pipeline {
+  _NoopPipeline(List<ModularStep> steps) : super(steps);
+
+  @override
+  Future<void> runStep(ModularStep step, Module module,
+          Map<Module, Set<DataId>> visibleData) =>
+      null;
+}
diff --git a/pkg/pkg.status b/pkg/pkg.status
index d26e5ee..5ad6e12 100644
--- a/pkg/pkg.status
+++ b/pkg/pkg.status
@@ -130,6 +130,7 @@
 [ $runtime != vm ]
 dev_compiler/test/options/*: SkipByDesign
 front_end/test/hot_reload_e2e_test: Skip
+modular_test/test/io_pipeline_test: SkipByDesign
 vm/test/*: SkipByDesign # Only meant to run on vm
 
 [ $system == linux ]
