// Copyright (c) 2022, 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.

// dart2wasmOptions=--extra-compiler-option=--enable-experimental-wasm-interop

import 'dart:_wasm';
import 'dart:js_util';

import 'package:expect/expect.dart';
import 'package:js/js.dart';

@JS()
external void eval(String code);

typedef SumTwoPositionalFun = String Function(String a, String b);
typedef SumOnePositionalAndOneOptionalFun = String Function(String a,
    [String? b]);
typedef SumTwoOptionalFun = String Function([String? a, String? b]);
typedef SumOnePositionalAndOneOptionalNonNullFun = String Function(String a,
    [String b]);
typedef SumTwoOptionalNonNullFun = String Function([String a, String b]);

@JS()
@staticInterop
class DartFromJSCallbackHelper {
  external factory DartFromJSCallbackHelper.factory(
      SumTwoPositionalFun sumTwoPositional,
      SumOnePositionalAndOneOptionalFun sumOnePositionalOneOptional,
      SumTwoOptionalFun sumTwoOptional,
      SumOnePositionalAndOneOptionalNonNullFun
          sumOnePositionalAndOneOptionalNonNull,
      SumTwoOptionalNonNullFun sumTwoOptionalNonNull);
}

extension DartFromJSCallbackHelperMethods on DartFromJSCallbackHelper {
  external String doSum1();
  external String doSum2(String a, String b);
  external String doSum3(Object summer);

  external String doSumOnePositionalAndOneOptionalA(String a);
  external String doSumOnePositionalAndOneOptionalB(String a, String b);
  external String doSumTwoOptionalA();
  external String doSumTwoOptionalB(String a);
  external String doSumTwoOptionalC(String a, String b);

  external String doSumOnePositionalAndOneOptionalANonNull(String a);
  external String doSumOnePositionalAndOneOptionalBNonNull(String a, String b);
  external String doSumTwoOptionalANonNull();
  external String doSumTwoOptionalBNonNull(String a);
  external String doSumTwoOptionalCNonNull(String a, String b);
}

String sumTwoPositional(String a, String b) {
  return a + b;
}

String sumOnePositionalAndOneOptional(String a, [String? b]) {
  return a + (b ?? 'bar');
}

String sumTwoOptional([String? a, String? b]) {
  return (a ?? 'foo') + (b ?? 'bar');
}

String sumOnePositionalAndOneOptionalNonNull(String a, [String b = 'bar']) {
  return a + b;
}

String sumTwoOptionalNonNull([String a = 'foo', String b = 'bar']) {
  return a + b;
}

void staticInteropCallbackTest() {
  eval(r'''
    globalThis.DartFromJSCallbackHelper = function(
        sumTwoPositional, sumOnePositionalOneOptional, sumTwoOptional,
        sumOnePositionalAndOneOptionalNonNull, sumTwoOptionalNonNull) {
      this.a = 'hello ';
      this.b = 'world!';
      this.sum = null;
      this.sumTwoPositional = sumTwoPositional;
      this.sumOnePositionalOneOptional = sumOnePositionalOneOptional;
      this.sumTwoOptional = sumTwoOptional;
      this.sumOnePositionalAndOneOptionalNonNull = sumOnePositionalAndOneOptionalNonNull;
      this.sumTwoOptionalNonNull = sumTwoOptionalNonNull;
      this.doSum1 = () => {
        return this.sumTwoPositional(this.a, this.b);
      }
      this.doSum2 = (a, b) => {
        return this.sumTwoPositional(a, b);
      }
      this.doSum3 = (summer) => {
        return summer(this.a, this.b);
      }
      this.doSumOnePositionalAndOneOptionalA = (a) => {
        return sumOnePositionalOneOptional(a);
      }
      this.doSumOnePositionalAndOneOptionalB = (a, b) => {
        return sumOnePositionalOneOptional(a, b);
      }
      this.doSumTwoOptionalA = () => {
        return sumTwoOptional();
      }
      this.doSumTwoOptionalB = (a) => {
        return sumTwoOptional(a);
      }
      this.doSumTwoOptionalC = (a, b) => {
        return sumTwoOptional(a, b);
      }
      this.doSumOnePositionalAndOneOptionalANonNull = (a) => {
        return sumOnePositionalAndOneOptionalNonNull(a);
      }
      this.doSumOnePositionalAndOneOptionalBNonNull = (a, b) => {
        return sumOnePositionalAndOneOptionalNonNull(a, b);
      }
      this.doSumTwoOptionalANonNull = () => {
        return sumTwoOptionalNonNull();
      }
      this.doSumTwoOptionalBNonNull = (a) => {
        return sumTwoOptionalNonNull(a);
      }
      this.doSumTwoOptionalCNonNull = (a, b) => {
        return sumTwoOptionalNonNull(a, b);
      }

    }
  ''');

  final helper = DartFromJSCallbackHelper.factory(
      allowInterop<SumTwoPositionalFun>(sumTwoPositional),
      allowInterop<SumOnePositionalAndOneOptionalFun>(
          sumOnePositionalAndOneOptional),
      allowInterop<SumTwoOptionalFun>(sumTwoOptional),
      allowInterop<SumOnePositionalAndOneOptionalNonNullFun>(
          sumOnePositionalAndOneOptionalNonNull),
      allowInterop<SumTwoOptionalNonNullFun>(sumTwoOptionalNonNull));

  Expect.equals('hello world!', helper.doSum1());
  Expect.equals('foobar', helper.doSum2('foo', 'bar'));
  Expect.equals('hello world!',
      helper.doSum3(allowInterop<SumTwoPositionalFun>((a, b) => a + b)));

  Expect.equals('foobar', helper.doSumOnePositionalAndOneOptionalA('foo'));
  Expect.equals(
      'foobar', helper.doSumOnePositionalAndOneOptionalB('foo', 'bar'));
  Expect.equals('foobar', helper.doSumTwoOptionalA());
  Expect.equals('foobar', helper.doSumTwoOptionalB('foo'));
  Expect.equals('foobar', helper.doSumTwoOptionalC('foo', 'bar'));

  Expect.equals(
      'foobar', helper.doSumOnePositionalAndOneOptionalANonNull('foo'));
  Expect.equals(
      'foobar', helper.doSumOnePositionalAndOneOptionalBNonNull('foo', 'bar'));
  Expect.equals('foobar', helper.doSumTwoOptionalANonNull());
  Expect.equals('foobar', helper.doSumTwoOptionalBNonNull('foo'));
  Expect.equals('foobar', helper.doSumTwoOptionalCNonNull('foo', 'bar'));
}

typedef NoArgsFun = String Function();
typedef OneArgFun = String Function(String arg);
typedef OnePositionalAndOneOptionalArgsFun = String Function(String arg,
    [String arg2]);
typedef TwoOptionalArgsFun = String Function([String arg, String arg2]);

class TornOffClass {
  String noArgs() {
    return 'foo';
  }

  String oneArg(String arg) {
    return arg;
  }

  String onePositionalAndOneOptionalArgs(String arg, [String arg2 = 'bar']) {
    return arg + arg2;
  }

  String twoOptionalArgs([String arg = 'foo', String? arg2]) {
    return arg + (arg2 ?? '');
  }
}

typedef OneArgFunB = String Function(double arg);
typedef OnePositionalAndOneOptionalArgsFunB = String Function(double arg,
    [String arg2]);
typedef TwoOptionalArgsFunB = String Function([double arg, String arg2]);

class GenericTornOffClass<T, V> {
  String noArgs() {
    return 'foo';
  }

  String oneArg(T arg) {
    return '$arg';
  }

  String onePositionalAndOneOptionalArgs(T arg, [V? arg2]) {
    return '$arg $arg2';
  }

  String twoOptionalArgs([T? arg, V? arg2]) {
    return '$arg $arg2';
  }
}

void allowInteropCallbackTest() {
  eval(r'''
    globalThis.doSum1 = function(summer) {
      return summer('foo', 'bar');
    }
    globalThis.doSum2 = function(a, b) {
      return globalThis.summer(a, b);
    }
    globalThis.doSumOnePositionalAndOneOptionalA = function(a) {
      return summer(a);
    }
    globalThis.doSumOnePositionalAndOneOptionalB = function(a, b) {
      return summer(a, b);
    }
    globalThis.doSumTwoOptionalA = function() {
      return summer();
    }
    globalThis.doSumTwoOptionalB = function(a) {
      return summer(a);
    }
    globalThis.doSumTwoOptionalC = function(a, b) {
      return summer(a, b);
    }
    globalThis.doSumOnePositionalAndOneOptionalANonNull = function(a) {
      return summer(a);
    }
    globalThis.doSumOnePositionalAndOneOptionalBNonNull = function(a, b) {
      return summer(a, b);
    }
    globalThis.doSumTwoOptionalANonNull = function() {
      return summer();
    }
    globalThis.doSumTwoOptionalBNonNull = function(a) {
      return summer(a);
    }
    globalThis.doSumTwoOptionalCNonNull = function(a, b) {
      return summer(a, b);
    }

    // tear off cases
    globalThis.tearOffNoArgs = function (f) {
      return f();
    }
    globalThis.tearOffOneArg = function (f) {
      return f('foo');
    }
    globalThis.tearOffOnePositionalAndOneOptionalArgsA = function (f) {
      return f('foo');
    }
    globalThis.tearOffOnePositionalAndOneOptionalArgsB = function (f) {
      return f('foo', 'baz');
    }
    globalThis.tearOffTwoOptionalArgsA = function (f) {
      return f('foo');
    }
    globalThis.tearOffTwoOptionalArgsB = function (f) {
      return f('foo', 'baz');
    }

    // tear off generic class cases
    globalThis.tearOffGenericNoArgs = function (f) {
      return f();
    }
    globalThis.tearOffGenericOneArg = function (f) {
      return f(1.0);
    }
    globalThis.tearOffGenericOnePositionalAndOneOptionalArgsA = function (f) {
      return f(1.0);
    }
    globalThis.tearOffGenericOnePositionalAndOneOptionalArgsB = function (f) {
      return f(1.0, 'baz');
    }
    globalThis.tearOffGenericTwoOptionalArgsA = function (f) {
      return f(1.0);
    }
    globalThis.tearOffGenericTwoOptionalArgsB = function (f) {
      return f(1.0, 'baz');
    }
  ''');

  // General
  {
    final interopCallback = allowInterop<SumTwoPositionalFun>((a, b) => a + b);
    Expect.equals('foobar',
        callMethod(globalThis, 'doSum1', [interopCallback]).toString());
    setProperty(globalThis, 'summer', interopCallback);
    Expect.equals(
        'foobar', callMethod(globalThis, 'doSum2', ['foo', 'bar']).toString());
    final roundTripCallback = getProperty(globalThis, 'summer');
    Expect.equals('foobar',
        (dartify(roundTripCallback) as SumTwoPositionalFun)('foo', 'bar'));
  }

  // 1 nullable optional argument
  {
    final interopCallback = allowInterop<SumOnePositionalAndOneOptionalFun>(
        (a, [b]) => a + (b ?? 'bar'));
    setProperty(globalThis, 'summer', interopCallback);
    Expect.equals(
        'foobar',
        callMethod(globalThis, 'doSumOnePositionalAndOneOptionalA', ['foo'])
            .toString());
    Expect.equals(
        'foobar',
        callMethod(
                globalThis, 'doSumOnePositionalAndOneOptionalB', ['foo', 'bar'])
            .toString());
  }

  // All nullable optional arguments
  {
    final interopCallback = allowInterop<SumTwoOptionalFun>(
        ([a, b]) => (a ?? 'foo') + (b ?? 'bar'));
    setProperty(globalThis, 'summer', interopCallback);
    Expect.equals(
        'foobar', callMethod(globalThis, 'doSumTwoOptionalA', []).toString());
    Expect.equals('foobar',
        callMethod(globalThis, 'doSumTwoOptionalB', ['foo']).toString());
    Expect.equals('foobar',
        callMethod(globalThis, 'doSumTwoOptionalC', ['foo', 'bar']).toString());
  }

  // 1 non-nullable optional argument
  {
    final interopCallback =
        allowInterop<SumOnePositionalAndOneOptionalNonNullFun>(
            (a, [b = 'bar']) => a + b);
    setProperty(globalThis, 'summer', interopCallback);
    Expect.equals(
        'foobar',
        callMethod(globalThis, 'doSumOnePositionalAndOneOptionalA', ['foo'])
            .toString());
    Expect.equals(
        'foobar',
        callMethod(
                globalThis, 'doSumOnePositionalAndOneOptionalB', ['foo', 'bar'])
            .toString());
  }

  // All non-nullable optional arguments
  {
    final interopCallback = allowInterop<SumTwoOptionalNonNullFun>(
        ([a = 'foo', b = 'bar']) => a + b);
    setProperty(globalThis, 'summer', interopCallback);
    Expect.equals(
        'foobar', callMethod(globalThis, 'doSumTwoOptionalA', []).toString());
    Expect.equals('foobar',
        callMethod(globalThis, 'doSumTwoOptionalB', ['foo']).toString());
    Expect.equals('foobar',
        callMethod(globalThis, 'doSumTwoOptionalC', ['foo', 'bar']).toString());
  }

  // Tear off cases
  // No args.
  {
    final t = TornOffClass();
    final interopCallback = allowInterop<NoArgsFun>(t.noArgs);
    Expect.equals(
        'foo', callMethod(globalThis, 'tearOffNoArgs', [interopCallback]));
  }

  // One arg.
  {
    final t = TornOffClass();
    final interopCallback = allowInterop<OneArgFun>(t.oneArg);
    Expect.equals(
        'foo', callMethod(globalThis, 'tearOffOneArg', [interopCallback]));
  }

  // One positional and one optional case A.
  {
    final t = TornOffClass();
    final interopCallback = allowInterop<OnePositionalAndOneOptionalArgsFun>(
        t.onePositionalAndOneOptionalArgs);
    Expect.equals(
        'foobar',
        callMethod(globalThis, 'tearOffOnePositionalAndOneOptionalArgsA',
            [interopCallback]));
  }

  // One positional and one optional case B.
  {
    final t = TornOffClass();
    final interopCallback = allowInterop<OnePositionalAndOneOptionalArgsFun>(
        t.onePositionalAndOneOptionalArgs);
    Expect.equals(
        'foobaz',
        callMethod(globalThis, 'tearOffOnePositionalAndOneOptionalArgsB',
            [interopCallback]));
  }

  // Two optional case A.
  {
    final t = TornOffClass();
    final interopCallback = allowInterop<TwoOptionalArgsFun>(t.twoOptionalArgs);
    Expect.equals('foo',
        callMethod(globalThis, 'tearOffTwoOptionalArgsA', [interopCallback]));
  }

  // Two optional case B.
  {
    final t = TornOffClass();
    final interopCallback = allowInterop<TwoOptionalArgsFun>(t.twoOptionalArgs);
    Expect.equals('foobaz',
        callMethod(globalThis, 'tearOffTwoOptionalArgsB', [interopCallback]));
  }

  // Tearoffs of generic classes.
  // No args.
  {
    final t = GenericTornOffClass<double, String>();
    final interopCallback = allowInterop<NoArgsFun>(t.noArgs);
    Expect.equals('foo',
        callMethod(globalThis, 'tearOffGenericNoArgs', [interopCallback]));
  }

  // One arg.
  {
    final t = GenericTornOffClass<double, String>();
    final interopCallback = allowInterop<OneArgFunB>(t.oneArg);
    Expect.equals('1.0',
        callMethod(globalThis, 'tearOffGenericOneArg', [interopCallback]));
  }

  // One positional and one optional case A.
  {
    final t = GenericTornOffClass<double, String>();
    final interopCallback = allowInterop<OnePositionalAndOneOptionalArgsFunB>(
        t.onePositionalAndOneOptionalArgs);
    Expect.equals(
        '1.0 null',
        callMethod(globalThis, 'tearOffGenericOnePositionalAndOneOptionalArgsA',
            [interopCallback]));
  }

  // One positional and one optional case B.
  {
    final t = GenericTornOffClass<double, String>();
    final interopCallback = allowInterop<OnePositionalAndOneOptionalArgsFunB>(
        t.onePositionalAndOneOptionalArgs);
    Expect.equals(
        '1.0 baz',
        callMethod(globalThis, 'tearOffGenericOnePositionalAndOneOptionalArgsB',
            [interopCallback]));
  }

  // Two optional case A.
  {
    final t = GenericTornOffClass<double, String>();
    final interopCallback =
        allowInterop<TwoOptionalArgsFunB>(t.twoOptionalArgs);
    Expect.equals(
        '1.0 null',
        callMethod(
            globalThis, 'tearOffGenericTwoOptionalArgsA', [interopCallback]));
  }

  // Two optional case B.
  {
    final t = GenericTornOffClass<double, String>();
    final interopCallback =
        allowInterop<TwoOptionalArgsFunB>(t.twoOptionalArgs);
    Expect.equals(
        '1.0 baz',
        callMethod(
            globalThis, 'tearOffGenericTwoOptionalArgsB', [interopCallback]));
  }
}

void main() {
  staticInteropCallbackTest();
  allowInteropCallbackTest();
}
