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

import 'package:file/file.dart';
import 'package:file/memory.dart';
import 'package:file/record_replay.dart';
import 'package:file/src/backends/record_replay/codecs.dart';
import 'package:file/src/backends/record_replay/common.dart' hide TypeMatcher;
import 'package:file/src/backends/record_replay/events.dart';
import 'package:file/src/backends/record_replay/mutable_recording.dart';
import 'package:file/src/backends/record_replay/recording_proxy_mixin.dart';
import 'package:file_testing/file_testing.dart';
import 'package:path/path.dart' as p;
import 'package:test/test.dart';

import 'common_tests.dart';
import 'record_replay_matchers.dart';

void main() {
  group('SupportingCode', () {
    _BasicClass delegate;
    _RecordingClass rc;
    MutableRecording recording;

    setUp(() {
      delegate = new _BasicClass();
      rc = new _RecordingClass(
        delegate: delegate,
        stopwatch: new _FakeStopwatch(10),
        destination: new MemoryFileSystem().directory('/tmp')..createSync(),
      );
      recording = rc.recording;
    });

    group('InvocationEvent', () {
      test('recordsAllPropertyGetMetadata', () {
        delegate.basicProperty = 'foo';
        String value = rc.basicProperty;
        expect(recording.events, hasLength(1));
        expect(
            recording.events[0],
            getsProperty('basicProperty')
                .on(rc)
                .withResult(value)
                .withTimestamp(10));
      });

      test('recordsAllPropertySetMetadata', () {
        rc.basicProperty = 'foo';
        expect(recording.events, hasLength(1));
        expect(
            recording.events[0],
            setsProperty('basicProperty')
                .on(rc)
                .toValue('foo')
                .withTimestamp(10));
      });

      test('recordsAllMethodInvocationMetadata', () {
        String result = rc.basicMethod('foo', namedArg: 'bar');
        expect(recording.events, hasLength(1));
        expect(
            recording.events[0],
            invokesMethod('basicMethod')
                .on(rc)
                .withPositionalArguments(<String>['foo'])
                .withNamedArgument('namedArg', 'bar')
                .withResult(result)
                .withTimestamp(10));
      });

      test('resultIncompleteUntilFutureCompletes', () async {
        delegate.basicProperty = 'foo';
        rc.futureProperty; // ignore: unawaited_futures
        expect(recording.events, hasLength(1));
        expect(
            recording.events[0],
            getsProperty('futureProperty')
                .on(rc)
                .withResult(isNull)
                .withTimestamp(10));
        await recording.events[0].done;
        expect(
            recording.events[0],
            getsProperty('futureProperty')
                .on(rc)
                .withResult('future.foo')
                .withTimestamp(10));
      });

      test('resultIncompleteUntilStreamCompletes', () async {
        Stream<String> stream = rc.streamMethod('foo', namedArg: 'bar');
        stream.listen((_) {});
        expect(recording.events, hasLength(1));
        expect(
            recording.events[0],
            invokesMethod('streamMethod')
                .on(rc)
                .withPositionalArguments(<String>['foo'])
                .withNamedArgument('namedArg', 'bar')
                .withResult(allOf(isList, isEmpty))
                .withTimestamp(10));
        await recording.events[0].done;
        expect(
            recording.events[0],
            invokesMethod('streamMethod')
                .on(rc)
                .withPositionalArguments(<String>['foo'])
                .withNamedArgument('namedArg', 'bar')
                .withResult(<String>['stream', 'foo', 'bar'])
                .withTimestamp(10));
      });
    });

    group('MutableRecording', () {
      group('flush', () {
        test('writesManifestToFileSystemAsJson', () async {
          rc.basicProperty = 'foo';
          String value = rc.basicProperty;
          rc.basicMethod(value, namedArg: 'bar');
          await recording.flush();
          List<Map<String, dynamic>> manifest = _loadManifest(recording);
          expect(manifest, hasLength(3));
          expect(manifest[0], <String, dynamic>{
            'type': 'set',
            'property': 'basicProperty=',
            'value': 'foo',
            'object': '_RecordingClass',
            'result': null,
            'error': null,
            'timestamp': 10,
          });
          expect(manifest[1], <String, dynamic>{
            'type': 'get',
            'property': 'basicProperty',
            'object': '_RecordingClass',
            'result': 'foo',
            'error': null,
            'timestamp': 11,
          });
          expect(manifest[2], <String, dynamic>{
            'type': 'invoke',
            'method': 'basicMethod',
            'positionalArguments': <String>['foo'],
            'namedArguments': <String, dynamic>{'namedArg': 'bar'},
            'object': '_RecordingClass',
            'result': 'foo.bar',
            'error': null,
            'timestamp': 12
          });
        });

        test('awaitsPendingResultsIndefinitelyByDefault', () async {
          rc.veryLongFutureMethod(); // ignore: unawaited_futures
          expect(recording.flush().timeout(const Duration(milliseconds: 50)),
              throwsA(const TypeMatcher<TimeoutException>()));
        });

        test('succeedsIfAwaitPendingResultsThatComplete', () async {
          rc.futureMethod('foo', namedArg: 'bar'); // ignore: unawaited_futures
          await recording.flush(
              pendingResultTimeout: const Duration(seconds: 30));
          List<Map<String, dynamic>> manifest = _loadManifest(recording);
          expect(manifest[0], containsPair('result', 'future.foo.bar'));
        });

        test('succeedsIfAwaitPendingResultsThatTimeout', () async {
          rc.veryLongFutureMethod(); // ignore: unawaited_futures
          DateTime before = new DateTime.now();
          await recording.flush(
              pendingResultTimeout: const Duration(milliseconds: 250));
          DateTime after = new DateTime.now();
          Duration delta = after.difference(before);
          List<Map<String, dynamic>> manifest = _loadManifest(recording);
          expect(manifest[0], containsPair('result', isNull));
          expect(delta.inMilliseconds, greaterThanOrEqualTo(250));
        });

        test('throwsIfAlreadyFlushing', () {
          rc.basicProperty = 'foo';
          recording.flush();
          expect(recording.flush(), throwsA(isStateError));
        });
      });
    });

    group('encode', () {
      test('performsDeepEncoding', () async {
        rc.basicProperty = 'foo';
        rc.basicProperty;
        rc.basicMethod('bar', namedArg: 'baz');
        await rc.futureProperty;
        await rc.futureMethod('qux', namedArg: 'quz');
        await rc.streamMethod('quux', namedArg: 'quuz').drain<void>();
        List<Map<String, dynamic>> manifest =
            await encode(recording.events).cast<Map<String, dynamic>>();
        expect(manifest[0], <String, dynamic>{
          'type': 'set',
          'property': 'basicProperty=',
          'value': 'foo',
          'object': '_RecordingClass',
          'result': isNull,
          'error': null,
          'timestamp': 10,
        });
        expect(manifest[1], <String, dynamic>{
          'type': 'get',
          'property': 'basicProperty',
          'object': '_RecordingClass',
          'result': 'foo',
          'error': null,
          'timestamp': 11,
        });
        expect(manifest[2], <String, dynamic>{
          'type': 'invoke',
          'method': 'basicMethod',
          'positionalArguments': <String>['bar'],
          'namedArguments': <String, String>{'namedArg': 'baz'},
          'object': '_RecordingClass',
          'result': 'bar.baz',
          'error': null,
          'timestamp': 12,
        });
        expect(manifest[3], <String, dynamic>{
          'type': 'get',
          'property': 'futureProperty',
          'object': '_RecordingClass',
          'result': 'future.foo',
          'error': null,
          'timestamp': 13,
        });
        expect(manifest[4], <String, dynamic>{
          'type': 'invoke',
          'method': 'futureMethod',
          'positionalArguments': <String>['qux'],
          'namedArguments': <String, String>{'namedArg': 'quz'},
          'object': '_RecordingClass',
          'result': 'future.qux.quz',
          'error': null,
          'timestamp': 14,
        });
        expect(manifest[5], <String, dynamic>{
          'type': 'invoke',
          'method': 'streamMethod',
          'positionalArguments': <String>['quux'],
          'namedArguments': <String, String>{'namedArg': 'quuz'},
          'object': '_RecordingClass',
          'result': <String>['stream', 'quux', 'quuz'],
          'error': null,
          'timestamp': 15,
        });
      });
    });

    group('deeplyEqual', () {
      Map<String, dynamic> newMap({
        String stringValue: 'foo',
        bool boolValue: true,
        String lastListValue: 'c',
        int lastMapValue: 2,
      }) {
        return <String, dynamic>{
          'string': stringValue,
          'bool': boolValue,
          'list': <String>['a', 'b', lastListValue],
          'map': <Symbol, int>{
            #foo: 1,
            #bar: lastMapValue,
          },
        };
      }

      test('primitives', () {
        expect(deeplyEqual(1, 1), isTrue);
        expect(deeplyEqual(1, 2), isFalse);
        expect(deeplyEqual('1', '1'), isTrue);
        expect(deeplyEqual('1', '2'), isFalse);
        expect(deeplyEqual(true, true), isTrue);
        expect(deeplyEqual(true, false), isFalse);
        expect(deeplyEqual(null, null), isTrue);
        expect(deeplyEqual(1, '1'), isFalse);
      });

      test('listOfPrimitives', () {
        expect(deeplyEqual(<int>[], <int>[]), isTrue);
        expect(deeplyEqual(<int>[1, 2, 3], <int>[1, 2, 3]), isTrue);
        expect(deeplyEqual(<int>[1, 2, 3], <int>[1, 3, 2]), isFalse);
        expect(deeplyEqual(<int>[1, 2, 3], <int>[1, 2]), isFalse);
        expect(deeplyEqual(<int>[1, 2, 3], <int>[1, 2, 3, 4]), isFalse);
        expect(deeplyEqual(<String>['a', 'b'], <String>['a', 'b']), isTrue);
        expect(deeplyEqual(<String>['a', 'b'], <String>['b', 'a']), isFalse);
        expect(deeplyEqual(<String>['a', 'b'], <String>['a']), isFalse);
        expect(deeplyEqual(<int>[], <dynamic>[]), isFalse);
        expect(deeplyEqual(<int>[], null), isFalse);
      });

      test('mapOfPrimitives', () {
        expect(deeplyEqual(<String, int>{}, <String, int>{}), isTrue);
        expect(deeplyEqual(<int, int>{1: 2}, <int, int>{1: 2}), isTrue);
        expect(deeplyEqual(<int, int>{1: 2}, <int, int>{1: 3}), isFalse);
        expect(deeplyEqual(<int, int>{1: 2}, <int, int>{}), isFalse);
        expect(deeplyEqual(<int, int>{}, <int, int>{1: 2}), isFalse);
        expect(deeplyEqual(<String, int>{}, <int, int>{}), isFalse);
        expect(deeplyEqual(<String, int>{}, <dynamic, dynamic>{}), isFalse);
        expect(deeplyEqual(<String, int>{}, null), isFalse);
      });

      test('listOfMaps', () {
        expect(deeplyEqual(newMap(), newMap()), isTrue);
        expect(deeplyEqual(newMap(), newMap(stringValue: 'bar')), isFalse);
        expect(deeplyEqual(newMap(), newMap(boolValue: false)), isFalse);
        expect(deeplyEqual(newMap(), newMap(lastListValue: 'd')), isFalse);
        expect(deeplyEqual(newMap(), newMap(lastMapValue: 3)), isFalse);
      });
    });
  });

  group('RecordingFileSystem', () {
    RecordingFileSystem fs;
    MemoryFileSystem delegate;
    LiveRecording recording;

    setUp(() {
      delegate = new MemoryFileSystem();
      fs = new RecordingFileSystem(
        delegate: delegate,
        destination: new MemoryFileSystem().directory('/tmp')..createSync(),
      );
      recording = fs.recording;
    });

    runCommonTests(
      () => fs,
      skip: <String>[
        'File > open', // Not yet implemented in MemoryFileSystem
      ],
    );

    group('recording', () {
      test('supportsMultipleActions', () {
        fs.directory('/foo').createSync();
        fs.file('/foo/bar').writeAsStringSync('BAR');
        List<InvocationEvent<dynamic>> events = recording.events;
        expect(events, hasLength(4));
        expect(events[0], invokesMethod('directory'));
        expect(events[1], invokesMethod('createSync'));
        expect(events[2], invokesMethod('file'));
        expect(events[3], invokesMethod('writeAsStringSync'));
        expect(events[0].result, events[1].object);
        expect(events[2].result, events[3].object);
      });

      group('FileSystem', () {
        test('directory', () {
          fs.directory('/foo');
          List<InvocationEvent<dynamic>> events = recording.events;
          expect(events, hasLength(1));
          expect(
            events[0],
            invokesMethod('directory').on(fs).withPositionalArguments(
                <String>['/foo']).withResult(isDirectory),
          );
        });

        test('file', () {
          fs.file('/foo');
          List<InvocationEvent<dynamic>> events = recording.events;
          expect(events, hasLength(1));
          expect(
            events[0],
            invokesMethod('file')
                .on(fs)
                .withPositionalArguments(<String>['/foo']).withResult(isFile),
          );
        });

        test('link', () {
          fs.link('/foo');
          List<InvocationEvent<dynamic>> events = recording.events;
          expect(events, hasLength(1));
          expect(
            events[0],
            invokesMethod('link')
                .on(fs)
                .withPositionalArguments(<String>['/foo']).withResult(isLink),
          );
        });

        test('path', () {
          fs.path;
          List<InvocationEvent<dynamic>> events = recording.events;
          expect(events, hasLength(1));
          expect(
            events[0],
            getsProperty('path')
                .on(fs)
                .withResult(const TypeMatcher<p.Context>()),
          );
        });

        test('systemTempDirectory', () {
          fs.systemTempDirectory;
          List<InvocationEvent<dynamic>> events = recording.events;
          expect(events, hasLength(1));
          expect(
              events[0],
              getsProperty('systemTempDirectory')
                  .on(fs)
                  .withResult(isDirectory));
        });

        group('currentDirectory', () {
          test('get', () {
            fs.currentDirectory;
            List<InvocationEvent<dynamic>> events = recording.events;
            expect(events, hasLength(1));
            expect(
                events[0],
                getsProperty('currentDirectory')
                    .on(fs)
                    .withResult(isDirectory));
          });

          test('setToString', () {
            delegate.directory('/foo').createSync();
            fs.currentDirectory = '/foo';
            List<InvocationEvent<dynamic>> events = recording.events;
            expect(events, hasLength(1));
            expect(events[0],
                setsProperty('currentDirectory').on(fs).toValue('/foo'));
          });

          test('setToRecordingDirectory', () {
            delegate.directory('/foo').createSync();
            fs.currentDirectory = fs.directory('/foo');
            List<InvocationEvent<dynamic>> events = recording.events;
            expect(events.length, greaterThanOrEqualTo(2));
            expect(events[0], invokesMethod().withResult(isDirectory));
            Directory directory = events[0].result;
            expect(
                events,
                contains(setsProperty('currentDirectory')
                    .on(fs)
                    .toValue(directory)));
          });

          test('setToNonRecordingDirectory', () {
            Directory dir = delegate.directory('/foo');
            dir.createSync();
            fs.currentDirectory = dir;
            List<InvocationEvent<dynamic>> events = recording.events;
            expect(events, hasLength(1));
            expect(events[0],
                setsProperty('currentDirectory').on(fs).toValue(isDirectory));
          });
        });

        test('stat', () async {
          delegate.file('/foo').createSync();
          await fs.stat('/foo');
          List<InvocationEvent<dynamic>> events = recording.events;
          expect(events, hasLength(1));
          expect(
            events[0],
            invokesMethod('stat').on(fs).withPositionalArguments(
                <String>['/foo']).withResult(isFileStat),
          );
        });

        test('statSync', () {
          delegate.file('/foo').createSync();
          fs.statSync('/foo');
          List<InvocationEvent<dynamic>> events = recording.events;
          expect(events, hasLength(1));
          expect(
            events[0],
            invokesMethod('statSync').on(fs).withPositionalArguments(
                <String>['/foo']).withResult(isFileStat),
          );
        });

        test('identical', () async {
          delegate.file('/foo').createSync();
          delegate.file('/bar').createSync();
          await fs.identical('/foo', '/bar');
          List<InvocationEvent<dynamic>> events = recording.events;
          expect(events, hasLength(1));
          expect(
              events[0],
              invokesMethod('identical').on(fs).withPositionalArguments(
                  <String>['/foo', '/bar']).withResult(isFalse));
        });

        test('identicalSync', () {
          delegate.file('/foo').createSync();
          delegate.file('/bar').createSync();
          fs.identicalSync('/foo', '/bar');
          List<InvocationEvent<dynamic>> events = recording.events;
          expect(events, hasLength(1));
          expect(
              events[0],
              invokesMethod('identicalSync').on(fs).withPositionalArguments(
                  <String>['/foo', '/bar']).withResult(isFalse));
        });

        test('isWatchSupported', () {
          fs.isWatchSupported;
          List<InvocationEvent<dynamic>> events = recording.events;
          expect(events, hasLength(1));
          expect(events[0],
              getsProperty('isWatchSupported').on(fs).withResult(isFalse));
        });

        test('type', () async {
          delegate.file('/foo').createSync();
          await fs.type('/foo');
          List<InvocationEvent<dynamic>> events = recording.events;
          expect(events, hasLength(1));
          expect(
              events[0],
              invokesMethod('type').on(fs).withPositionalArguments(
                  <String>['/foo']).withResult(FileSystemEntityType.file));
        });

        test('typeSync', () {
          delegate.file('/foo').createSync();
          fs.typeSync('/foo');
          List<InvocationEvent<dynamic>> events = recording.events;
          expect(events, hasLength(1));
          expect(
              events[0],
              invokesMethod('typeSync').on(fs).withPositionalArguments(
                  <String>['/foo']).withResult(FileSystemEntityType.file));
        });
      });

      group('Directory', () {
        test('create', () async {
          await fs.directory('/foo').create();
          expect(
              recording.events,
              contains(invokesMethod('create')
                  .on(isDirectory)
                  .withNamedArgument('recursive', false)
                  .withResult(isDirectory)));
        });

        test('createSync', () {
          fs.directory('/foo').createSync();
          expect(
              recording.events,
              contains(invokesMethod('createSync')
                  .on(isDirectory)
                  .withNamedArgument('recursive', false)
                  .withResult(isNull)));
        });

        test('list', () async {
          await delegate.directory('/foo').create();
          await delegate.directory('/bar').create();
          await delegate.file('/baz').create();
          Stream<FileSystemEntity> stream = fs.directory('/').list();
          await stream.drain<void>();
          expect(
            recording.events,
            contains(invokesMethod('list')
                .on(isDirectory)
                .withNamedArgument('recursive', false)
                .withNamedArgument('followLinks', true)
                .withResult(hasLength(3))),
          );
        });
      });

      group('File', () {
        // TODO(tvolkert): Fill in these test stubs
        test('create', () {});

        test('createSync', () {});

        test('rename', () {});

        test('renameSync', () {});

        test('copy', () {});

        test('copySync', () {});

        test('length', () {});

        test('lengthSync', () {});

        test('absolute', () {});

        test('lastModified', () {});

        test('lastModifiedSync', () {});

        test('open', () {});

        test('openSync', () {});

        test('openRead', () async {
          String content = 'Hello\nWorld';
          await delegate.file('/foo').writeAsString(content, flush: true);
          Stream<List<int>> stream = fs.file('/foo').openRead();
          await stream.drain<void>();
          expect(
              recording.events,
              contains(invokesMethod('openRead')
                  .on(isFile)
                  .withPositionalArguments(<int>[null, null])
                  .withNoNamedArguments()
                  .withResult(isList)));
          await recording.flush();
          List<Map<String, dynamic>> manifest = _loadManifest(recording);
          expect(manifest, hasLength(2));
          expect(
              manifest[1],
              allOf(
                containsPair('type', 'invoke'),
                containsPair('method', 'openRead'),
                containsPair('object', matches(r'^RecordingFile@[0-9]+$')),
                containsPair('positionalArguments', <int>[null, null]),
                containsPair('namedArguments', isEmpty),
                containsPair('result', matches(r'^![0-9]+.foo$')),
              ));
          File file = _getRecordingFile(recording, manifest[1]['result']);
          expect(file, exists);
          expect(await file.readAsString(), content);
        });

        test('openWrite', () {});

        test('readAsBytes', () async {
          String content = 'Hello\nWorld';
          await delegate.file('/foo').writeAsString(content, flush: true);
          await fs.file('/foo').readAsBytes();
          expect(
              recording.events,
              contains(invokesMethod('readAsBytes')
                  .on(isFile)
                  .withNoNamedArguments()
                  .withResult(allOf(isList, hasLength(content.length)))));
          await recording.flush();
          List<Map<String, dynamic>> manifest = _loadManifest(recording);
          expect(manifest, hasLength(2));
          expect(
              manifest[1],
              allOf(
                containsPair('type', 'invoke'),
                containsPair('method', 'readAsBytes'),
                containsPair('object', matches(r'^RecordingFile@[0-9]+$')),
                containsPair('positionalArguments', isEmpty),
                containsPair('namedArguments', isEmpty),
                containsPair('result', matches(r'^![0-9]+.foo$')),
              ));
          File file = _getRecordingFile(recording, manifest[1]['result']);
          expect(file, exists);
          expect(await file.readAsString(), content);
        });

        test('readAsBytesSync', () async {
          String content = 'Hello\nWorld';
          await delegate.file('/foo').writeAsString(content, flush: true);
          fs.file('/foo').readAsBytesSync();
          expect(
              recording.events,
              contains(invokesMethod('readAsBytesSync')
                  .on(isFile)
                  .withNoNamedArguments()
                  .withResult(allOf(isList, hasLength(content.length)))));
          await recording.flush();
          List<Map<String, dynamic>> manifest = _loadManifest(recording);
          expect(manifest, hasLength(2));
          expect(
              manifest[1],
              allOf(
                containsPair('type', 'invoke'),
                containsPair('method', 'readAsBytesSync'),
                containsPair('object', matches(r'^RecordingFile@[0-9]+$')),
                containsPair('positionalArguments', isEmpty),
                containsPair('namedArguments', isEmpty),
                containsPair('result', matches(r'^![0-9]+.foo$')),
              ));
          File file = _getRecordingFile(recording, manifest[1]['result']);
          expect(file, exists);
          expect(await file.readAsString(), content);
        });

        test('readAsString', () async {
          String content = 'Hello\nWorld';
          await delegate
              .file('/foo')
              .writeAsString(content, encoding: latin1, flush: true);
          await fs.file('/foo').readAsString(encoding: latin1);
          expect(
              recording.events,
              contains(invokesMethod('readAsString')
                  .on(isFile)
                  .withNamedArgument('encoding', latin1)
                  .withResult(content)));
          await recording.flush();
          List<Map<String, dynamic>> manifest = _loadManifest(recording);
          expect(manifest, hasLength(2));
          expect(
              manifest[1],
              allOf(
                containsPair('type', 'invoke'),
                containsPair('method', 'readAsString'),
                containsPair('object', matches(r'^RecordingFile@[0-9]+$')),
                containsPair('positionalArguments', isEmpty),
                containsPair('result', matches(r'^![0-9]+.foo$')),
                containsPair(
                    'namedArguments',
                    allOf(
                      hasLength(1),
                      containsPair('encoding', 'iso-8859-1'),
                    )),
              ));
          File file = _getRecordingFile(recording, manifest[1]['result']);
          expect(file, exists);
          expect(await file.readAsString(), content);
        });

        test('readAsStringSync', () async {
          String content = 'Hello\nWorld';
          await delegate
              .file('/foo')
              .writeAsString(content, encoding: latin1, flush: true);
          fs.file('/foo').readAsStringSync(encoding: latin1);
          expect(
              recording.events,
              contains(invokesMethod('readAsStringSync')
                  .on(isFile)
                  .withNamedArgument('encoding', latin1)
                  .withResult(content)));
          await recording.flush();
          List<Map<String, dynamic>> manifest = _loadManifest(recording);
          expect(manifest, hasLength(2));
          expect(
              manifest[1],
              allOf(
                containsPair('type', 'invoke'),
                containsPair('method', 'readAsStringSync'),
                containsPair('object', matches(r'^RecordingFile@[0-9]+$')),
                containsPair('positionalArguments', isEmpty),
                containsPair('result', matches(r'^![0-9]+.foo$')),
                containsPair(
                    'namedArguments',
                    allOf(
                      hasLength(1),
                      containsPair('encoding', 'iso-8859-1'),
                    )),
              ));
          File file = _getRecordingFile(recording, manifest[1]['result']);
          expect(file, exists);
          expect(await file.readAsString(), content);
        });

        test('readAsLines', () async {
          String content = 'Hello\nWorld';
          await delegate.file('/foo').writeAsString(content, flush: true);
          await fs.file('/foo').readAsLines();
          expect(
              recording.events,
              contains(invokesMethod('readAsLines')
                  .on(isFile)
                  .withNamedArgument('encoding', utf8)
                  .withResult(<String>['Hello', 'World'])));
          await recording.flush();
          List<Map<String, dynamic>> manifest = _loadManifest(recording);
          expect(manifest, hasLength(2));
          expect(
              manifest[1],
              allOf(
                containsPair('type', 'invoke'),
                containsPair('method', 'readAsLines'),
                containsPair('object', matches(r'^RecordingFile@[0-9]+$')),
                containsPair('positionalArguments', isEmpty),
                containsPair('result', matches(r'^![0-9]+.foo$')),
                containsPair(
                    'namedArguments', <String, String>{'encoding': 'utf-8'}),
              ));
          File file = _getRecordingFile(recording, manifest[1]['result']);
          expect(file, exists);
          expect(await file.readAsString(), content);
        });

        test('readAsLinesSync', () async {
          String content = 'Hello\nWorld';
          await delegate.file('/foo').writeAsString(content, flush: true);
          fs.file('/foo').readAsLinesSync();
          expect(
              recording.events,
              contains(invokesMethod('readAsLinesSync')
                  .on(isFile)
                  .withNamedArgument('encoding', utf8)
                  .withResult(<String>['Hello', 'World'])));
          await recording.flush();
          List<Map<String, dynamic>> manifest = _loadManifest(recording);
          expect(manifest, hasLength(2));
          expect(
              manifest[1],
              allOf(
                containsPair('type', 'invoke'),
                containsPair('method', 'readAsLinesSync'),
                containsPair('object', matches(r'^RecordingFile@[0-9]+$')),
                containsPair('positionalArguments', isEmpty),
                containsPair('result', matches(r'^![0-9]+.foo$')),
                containsPair('namedArguments', {'encoding': 'utf-8'}),
              ));
          File file = _getRecordingFile(recording, manifest[1]['result']);
          expect(file, exists);
          expect(await file.readAsString(), content);
        });

        test('writeAsBytes', () {});

        test('writeAsBytesSync', () {});

        test('writeAsString', () {});

        test('writeAsStringSync', () {});
      });

      group('Link', () {});
    });
  });
}

List<Map<String, dynamic>> _loadManifest(LiveRecording recording) {
  List<FileSystemEntity> files = recording.destination.listSync();
  File manifestFile = files.singleWhere(
      (FileSystemEntity entity) => entity.basename == kManifestName);
  return new JsonDecoder()
      .convert(manifestFile.readAsStringSync())
      .cast<Map<String, dynamic>>();
}

File _getRecordingFile(LiveRecording recording, String manifestReference) {
  expect(manifestReference, startsWith('!'));
  String basename = manifestReference.substring(1);
  String dirname = recording.destination.path;
  String path = recording.destination.fileSystem.path.join(dirname, basename);
  return recording.destination.fileSystem.file(path);
}

class _BasicClass {
  String basicProperty;

  Future<String> get futureProperty async => 'future.$basicProperty';

  String basicMethod(String positionalArg, {String namedArg}) =>
      '$positionalArg.$namedArg';

  Future<String> futureMethod(String positionalArg, {String namedArg}) async {
    await new Future<Null>.delayed(const Duration(milliseconds: 500));
    String basicValue = basicMethod(positionalArg, namedArg: namedArg);
    return 'future.$basicValue';
  }

  Stream<String> streamMethod(String positionalArg, {String namedArg}) async* {
    yield 'stream';
    yield positionalArg;
    yield namedArg;
  }

  Future<String> veryLongFutureMethod() async {
    await new Future<Null>.delayed(const Duration(seconds: 1));
    return 'future';
  }

  Stream<String> infiniteStreamMethod() async* {
    yield 'stream';
    int i = 0;
    while (i >= 0) {
      yield '${i++}';
      await new Future<Null>.delayed(const Duration(seconds: 1));
    }
  }
}

class _RecordingClass extends Object
    with RecordingProxyMixin
    implements _BasicClass {
  final _BasicClass delegate;

  _RecordingClass({
    this.delegate,
    this.stopwatch,
    Directory destination,
  }) : recording = new MutableRecording(destination) {
    methods.addAll(<Symbol, Function>{
      #basicMethod: delegate.basicMethod,
      #futureMethod: delegate.futureMethod,
      #streamMethod: delegate.streamMethod,
      #veryLongFutureMethod: delegate.veryLongFutureMethod,
      #infiniteStreamMethod: delegate.infiniteStreamMethod,
    });

    properties.addAll(<Symbol, Function>{
      #basicProperty: () => delegate.basicProperty,
      const Symbol('basicProperty='): (String value) {
        delegate.basicProperty = value;
      },
      #futureProperty: () => delegate.futureProperty,
    });
  }

  @override
  String get identifier => '$runtimeType';

  @override
  final MutableRecording recording;

  @override
  final Stopwatch stopwatch;
}

class _FakeStopwatch implements Stopwatch {
  int _value;

  _FakeStopwatch(this._value);

  @override
  int get elapsedMilliseconds => _value++;

  @override
  dynamic noSuchMethod(Invocation invocation) => super.noSuchMethod(invocation);
}
