// Copyright 2013 The Flutter Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

// KEEP THIS SYNCHRONIZED WITH ../../lib/web_ui/test/channel_buffers_test.dart

import 'dart:async';
import 'dart:convert';
import 'dart:typed_data';
import 'dart:ui' as ui;

import 'package:litetest/litetest.dart';

ByteData _makeByteData(String str) {
  final Uint8List list = utf8.encode(str);
  final ByteBuffer buffer = list.buffer;
  return ByteData.view(buffer);
}

void _resize(ui.ChannelBuffers buffers, String name, int newSize) {
  buffers.handleMessage(_makeByteData('resize\r$name\r$newSize'));
}

void main() {
  bool assertsEnabled = false;
  assert(() {
    assertsEnabled = true;
    return true;
  }());

  test('push drain', () async {
    const String channel = 'foo';
    final ByteData data = _makeByteData('bar');
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    bool called = false;
    void callback(ByteData? responseData) {
      called = true;
    }
    buffers.push(channel, data, callback);
    // Ignoring the deprecated member use because we're specifically testing
    // deprecated API.
    // ignore: deprecated_member_use
    await buffers.drain(channel, (ByteData? drainedData, ui.PlatformMessageResponseCallback drainedCallback) async {
      expect(drainedData, equals(data));
      expect(called, isFalse);
      drainedCallback(drainedData);
      expect(called, isTrue);
    });
  });

  test('drain is sync', () async {
    const String channel = 'foo';
    final ByteData data = _makeByteData('message');
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    void callback(ByteData? responseData) {}
    buffers.push(channel, data, callback);
    final List<String> log = <String>[];
    final Completer<void> completer = Completer<void>();
    scheduleMicrotask(() { log.add('before drain, microtask'); });
    log.add('before drain');

    // Ignoring the returned future because the completion of the drain is
    // communicated using the `completer`.
    // Ignoring the deprecated member use because we're specifically testing
    // deprecated API.
    // ignore: deprecated_member_use
    buffers.drain(channel, (ByteData? drainedData, ui.PlatformMessageResponseCallback drainedCallback) async {
      log.add('callback');
      completer.complete();
    });
    log.add('after drain, before await');
    await completer.future;
    log.add('after await');
    expect(log, <String>[
      'before drain',
      'callback',
      'after drain, before await',
      'before drain, microtask',
      'after await'
    ]);
  });

  test('push drain zero', () async {
    const String channel = 'foo';
    final ByteData data = _makeByteData('bar');
    final
    ui.ChannelBuffers buffers = ui.ChannelBuffers();
    void callback(ByteData? responseData) {}
    _resize(buffers, channel, 0);
    buffers.push(channel, data, callback);
    bool didCall = false;
    // Ignoring the deprecated member use because we're specifically testing
    // deprecated API.
    // ignore: deprecated_member_use
    await buffers.drain(channel, (ByteData? drainedData, ui.PlatformMessageResponseCallback drainedCallback) async {
      didCall = true;
    });
    expect(didCall, equals(false));
  });

  test('drain when empty', () async {
    const String channel = 'foo';
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    bool didCall = false;
    // Ignoring the deprecated member use because we're specifically testing
    // deprecated API.
    // ignore: deprecated_member_use
    await buffers.drain(channel, (ByteData? drainedData, ui.PlatformMessageResponseCallback drainedCallback) async {
      didCall = true;
    });
    expect(didCall, equals(false));
  });

  test('overflow', () async {
    const String channel = 'foo';
    final ByteData one = _makeByteData('one');
    final ByteData two = _makeByteData('two');
    final ByteData three = _makeByteData('three');
    final ByteData four = _makeByteData('four');
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    void callback(ByteData? responseData) {}
    _resize(buffers, channel, 3);
    buffers.push(channel, one, callback);
    buffers.push(channel, two, callback);
    buffers.push(channel, three, callback);
    buffers.push(channel, four, callback);
    int counter = 0;
    // Ignoring the deprecated member use because we're specifically testing
    // deprecated API.
    // ignore: deprecated_member_use
    await buffers.drain(channel, (ByteData? drainedData, ui.PlatformMessageResponseCallback drainedCallback) async {
      switch (counter) {
        case 0:
          expect(drainedData, equals(two));
        case 1:
          expect(drainedData, equals(three));
        case 2:
          expect(drainedData, equals(four));
      }
      counter += 1;
    });
    expect(counter, equals(3));
  });

  test('resize drop', () async {
    const String channel = 'foo';
    final ByteData one = _makeByteData('one');
    final ByteData two = _makeByteData('two');
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    _resize(buffers, channel, 100);
    void callback(ByteData? responseData) {}
    buffers.push(channel, one, callback);
    buffers.push(channel, two, callback);
    _resize(buffers, channel, 1);
    int counter = 0;
    // Ignoring the deprecated member use because we're specifically testing
    // deprecated API.
    // ignore: deprecated_member_use
    await buffers.drain(channel, (ByteData? drainedData, ui.PlatformMessageResponseCallback drainedCallback) async {
      switch (counter) {
        case 0:
          expect(drainedData, equals(two));
      }
      counter += 1;
    });
    expect(counter, equals(1));
  });

  test('resize dropping calls callback', () async {
    const String channel = 'foo';
    final ByteData one = _makeByteData('one');
    final ByteData two = _makeByteData('two');
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    bool didCallCallback = false;
    void oneCallback(ByteData? responseData) {
      expect(responseData, isNull);
      didCallCallback = true;
    }
    void twoCallback(ByteData? responseData) {
      fail('wrong callback called');
    }
    _resize(buffers, channel, 100);
    buffers.push(channel, one, oneCallback);
    buffers.push(channel, two, twoCallback);
    expect(didCallCallback, equals(false));
    _resize(buffers, channel, 1);
    expect(didCallCallback, equals(true));
  });

  test('overflow calls callback', () async {
    const String channel = 'foo';
    final ByteData one = _makeByteData('one');
    final ByteData two = _makeByteData('two');
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    bool didCallCallback = false;
    void oneCallback(ByteData? responseData) {
      expect(responseData, isNull);
      didCallCallback = true;
    }
    void twoCallback(ByteData? responseData) {
      fail('wrong callback called');
    }
    _resize(buffers, channel, 1);
    buffers.push(channel, one, oneCallback);
    buffers.push(channel, two, twoCallback);
    expect(didCallCallback, equals(true));
  });

  test('handle garbage', () async {
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    expect(() => buffers.handleMessage(_makeByteData('asdfasdf')),
           throwsException);
  });

  test('handle resize garbage', () async {
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    expect(() => buffers.handleMessage(_makeByteData('resize\rfoo\rbar')),
           throwsException);
  });

  test('ChannelBuffers.setListener', () async {
    final List<String> log = <String>[];
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    final ByteData one = _makeByteData('one');
    final ByteData two = _makeByteData('two');
    final ByteData three = _makeByteData('three');
    final ByteData four = _makeByteData('four');
    final ByteData five = _makeByteData('five');
    final ByteData six = _makeByteData('six');
    final ByteData seven = _makeByteData('seven');
    buffers.push('a', one, (ByteData? data) { });
    buffers.push('b', two, (ByteData? data) { });
    buffers.push('a', three, (ByteData? data) { });
    log.add('top');
    buffers.setListener('a', (ByteData? data, ui.PlatformMessageResponseCallback callback) {
      expect(data, isNotNull);
      log.add('a1: ${utf8.decode(data!.buffer.asUint8List())}');
    });
    log.add('-1');
    await null;
    log.add('-2');
    buffers.setListener('a', (ByteData? data, ui.PlatformMessageResponseCallback callback) {
      expect(data, isNotNull);
      log.add('a2: ${utf8.decode(data!.buffer.asUint8List())}');
    });
    log.add('-3');
    await null;
    log.add('-4');
    buffers.setListener('b', (ByteData? data, ui.PlatformMessageResponseCallback callback) {
      expect(data, isNotNull);
      log.add('b: ${utf8.decode(data!.buffer.asUint8List())}');
    });
    log.add('-5');
    await null; // first microtask after setting listener drains the first message
    await null; // second microtask ends the draining.
    log.add('-6');
    buffers.push('b', four, (ByteData? data) { });
    buffers.push('a', five, (ByteData? data) { });
    log.add('-7');
    await null;
    log.add('-8');
    buffers.clearListener('a');
    buffers.push('a', six, (ByteData? data) { });
    buffers.push('b', seven, (ByteData? data) { });
    await null;
    log.add('-9');
    expect(log, <String>[
      'top',
      '-1',
      'a1: three',
      '-2',
      '-3',
      '-4',
      '-5',
      'b: two',
      '-6',
      'b: four',
      'a2: five',
      '-7',
      '-8',
      'b: seven',
      '-9',
    ]);
  });

  test('ChannelBuffers.clearListener', () async {
    final List<String> log = <String>[];
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    final ByteData one = _makeByteData('one');
    final ByteData two = _makeByteData('two');
    final ByteData three = _makeByteData('three');
    final ByteData four = _makeByteData('four');
    buffers.handleMessage(_makeByteData('resize\ra\r10'));
    buffers.push('a', one, (ByteData? data) { });
    buffers.push('a', two, (ByteData? data) { });
    buffers.push('a', three, (ByteData? data) { });
    log.add('-1');
    buffers.setListener('a', (ByteData? data, ui.PlatformMessageResponseCallback callback) {
      expect(data, isNotNull);
      log.add('a1: ${utf8.decode(data!.buffer.asUint8List())}');
    });
    await null; // handles one
    log.add('-2');
    buffers.clearListener('a');
    await null;
    log.add('-3');
    buffers.setListener('a', (ByteData? data, ui.PlatformMessageResponseCallback callback) {
      expect(data, isNotNull);
      log.add('a2: ${utf8.decode(data!.buffer.asUint8List())}');
    });
    log.add('-4');
    await null;
    buffers.push('a', four, (ByteData? data) { });
    log.add('-5');
    await null;
    log.add('-6');
    await null;
    log.add('-7');
    await null;
    expect(log, <String>[
      '-1',
      'a1: one',
      '-2',
      '-3',
      '-4',
      'a2: two',
      '-5',
      'a2: three',
      '-6',
      'a2: four',
      '-7',
    ]);
  });

  test('ChannelBuffers.handleMessage for resize', () async {
    final List<String> log = <String>[];
    final ui.ChannelBuffers buffers = _TestChannelBuffers(log);
    // Created as follows:
    //   print(StandardMethodCodec().encodeMethodCall(MethodCall('resize', ['abcdef', 12345])).buffer.asUint8List());
    // ...with three 0xFF bytes on either side to ensure the method works with an offset on the underlying buffer.
    buffers.handleMessage(ByteData.sublistView(Uint8List.fromList(<int>[255, 255, 255, 7, 6, 114, 101, 115, 105, 122, 101, 12, 2, 7, 6, 97, 98, 99, 100, 101, 102, 3, 57, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 255, 255]), 3, 27));
    expect(log, const <String>['resize abcdef 12345']);
  });

  test('ChannelBuffers.handleMessage for overflow', () async {
    final List<String> log = <String>[];
    final ui.ChannelBuffers buffers = _TestChannelBuffers(log);
    // Created as follows:
    //   print(StandardMethodCodec().encodeMethodCall(MethodCall('overflow', ['abcdef', false])).buffer.asUint8List());
    // ...with three 0xFF bytes on either side to ensure the method works with an offset on the underlying buffer.
    buffers.handleMessage(ByteData.sublistView(Uint8List.fromList(<int>[255, 255, 255, 7, 8, 111, 118, 101, 114, 102, 108, 111, 119, 12, 2, 7, 6, 97, 98, 99, 100, 101, 102, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 255, 255, 255]), 3, 24));
    expect(log, const <String>['allowOverflow abcdef false']);
  });

  test('ChannelBuffers uses the right zones', () async {
    final List<String> log = <String>[];
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    final Zone zone1 = Zone.current.fork();
    final Zone zone2 = Zone.current.fork();
    zone1.run(() {
      log.add('first zone run: ${Zone.current == zone1}');
      buffers.setListener('a', (ByteData? data, ui.PlatformMessageResponseCallback callback) {
        log.add('callback1: ${Zone.current == zone1}');
        callback(data);
      });
    });
    zone2.run(() {
      log.add('second zone run: ${Zone.current == zone2}');
      buffers.push('a', ByteData.sublistView(Uint8List.fromList(<int>[]), 0, 0), (ByteData? data) {
        log.add('callback2: ${Zone.current == zone2}');
      });
    });
    await null;
    expect(log, <String>[
      'first zone run: true',
      'second zone run: true',
      'callback1: true',
      'callback2: true',
    ]);
  });

  test('ChannelBufferspush rejects names with nulls', () async {
    const String channel = 'foo\u0000bar';
    final ByteData blabla = _makeByteData('blabla');
    final ui.ChannelBuffers buffers = ui.ChannelBuffers();
    try {
      buffers.push(channel, blabla, (ByteData? data) { });
      fail('did not throw as expected');
    } on AssertionError catch (e) {
      expect(e.toString(), contains('U+0000 NULL'));
    }
    try {
      buffers.setListener(channel, (ByteData? data, ui.PlatformMessageResponseCallback callback) { });
      fail('did not throw as expected');
    } on AssertionError catch (e) {
      expect(e.toString(), contains('U+0000 NULL'));
    }
  }, skip: !assertsEnabled);
}

class _TestChannelBuffers extends ui.ChannelBuffers {
  _TestChannelBuffers(this.log);

  final List<String> log;

  @override
  void resize(String name, int newSize) {
    log.add('resize $name $newSize');
  }

  @override
  void allowOverflow(String name, bool allowed) {
    log.add('allowOverflow $name $allowed');
  }
}
