// 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.

import 'package:analyzer/dart/analysis/features.dart';
import 'package:analyzer/src/dart/analysis/experiments.dart';
import 'package:analyzer/src/error/codes.dart';
import 'package:analyzer/src/generated/engine.dart';
import 'package:test_reflective_loader/test_reflective_loader.dart';

import '../../generated/test_support.dart';
import '../dart/resolution/driver_resolution.dart';

main() {
  defineReflectiveSuite(() {
    defineReflectiveTests(UseOfVoidResultTest);
    defineReflectiveTests(UseOfVoidResultWithExtensionMethodsTest);
    defineReflectiveTests(UseOfVoidResultTest_NonNullable);
  });
}

@reflectiveTest
class UseOfVoidResultTest extends DriverResolutionTest {
  test_andVoidLhsError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  x && true;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 26, 1),
    ]);
  }

  test_andVoidRhsError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  true && x;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 34, 1),
    ]);
  }

  test_assignmentExpression_function() async {
    await assertErrorsInCode('''
void f() {}
class A {
  n() {
    var a;
    a = f();
  }
}''', [
      error(HintCode.UNUSED_LOCAL_VARIABLE, 38, 1),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 49, 1),
    ]);
  }

  test_assignmentExpression_method() async {
    await assertErrorsInCode('''
class A {
  void m() {}
  n() {
    var a;
    a = m();
  }
}''', [
      error(HintCode.UNUSED_LOCAL_VARIABLE, 40, 1),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 51, 1),
    ]);
  }

  test_assignmentToVoidParameterOk() async {
    // Note: the spec may decide to disallow this, but at this point that seems
    // highly unlikely.
    await assertNoErrorsInCode('''
void main() {
  void x;
  f(x);
}
void f(void x) {}
''');
  }

  test_assignToVoid_notStrong_error() async {
    // See StrongModeStaticTypeAnalyzer2Test.test_assignToVoidOk
    // for testing that this does not have errors in strong mode.
    await assertNoErrorsInCode('''
void main() {
  void x;
  x = 42;
}
''');
  }

  test_await() async {
    await assertNoErrorsInCode('''
main() async {
  void x;
  await x;
}''');
  }

  test_implicitReturnValue() async {
    await assertNoErrorsInCode(r'''
f() {}
class A {
  n() {
    var a = f();
  }
}
''');
  }

  test_inForLoop_error() async {
    await assertErrorsInCode('''
class A {
  void m() {}
  n() {
    for(Object a = m();;) {}
  }
}''', [
      error(HintCode.UNUSED_LOCAL_VARIABLE, 47, 1),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 51, 1),
    ]);
  }

  test_inForLoop_ok() async {
    await assertNoErrorsInCode('''
class A {
  void m() {}
  n() {
    for(void a = m();;) {}
  }
}''');
  }

  test_interpolateVoidValueError() async {
    await assertErrorsInCode(r'''
void main() {
  void x;
  "$x";
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 28, 1),
    ]);
  }

  test_negateVoidValueError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  !x;
}
''', [
      error(HintCode.UNUSED_LOCAL_VARIABLE, 21, 1),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 27, 1),
    ]);
  }

  test_nonVoidReturnValue() async {
    await assertNoErrorsInCode(r'''
int f() => 1;
g() {
  var a = f();
}
''');
  }

  test_orVoidLhsError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  x || true;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 26, 1),
    ]);
  }

  test_orVoidRhsError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  false || x;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 35, 1),
    ]);
  }

  test_throwVoidValueError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  throw x;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 32, 1),
    ]);
  }

  test_unaryNegativeVoidValueError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  -x;
}
''', [
      // TODO(mfairhurst) suppress UNDEFINED_OPERATOR
      error(HintCode.UNUSED_LOCAL_VARIABLE, 21, 1),
      error(StaticTypeWarningCode.UNDEFINED_OPERATOR, 26, 1),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 27, 1),
    ]);
  }

  test_useOfInForeachIterableError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  for (var v in x) {}
}
''', [
      error(HintCode.UNUSED_LOCAL_VARIABLE, 35, 1),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 40, 1),
    ]);
  }

  test_useOfVoidAsIndexAssignError() async {
    await assertErrorsInCode('''
void main(List list) {
  void x;
  list[x] = null;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 40, 1),
    ]);
  }

  test_useOfVoidAsIndexError() async {
    await assertErrorsInCode('''
void main(List list) {
  void x;
  list[x];
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 40, 1),
    ]);
  }

  test_useOfVoidAssignedToDynamicError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  dynamic z = x;
}
''', [
      error(HintCode.UNUSED_LOCAL_VARIABLE, 34, 1),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 38, 1),
    ]);
  }

  test_useOfVoidByIndexingError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  x[0];
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 27, 3),
    ]);
  }

  test_useOfVoidCallSetterError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  x.foo = null;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 28, 3),
    ]);
  }

  test_useOfVoidCastsOk() async {
    await assertNoErrorsInCode('''
void use(dynamic x) { }
void main() {
  void x;
  use(x as int);
}
''');
  }

  test_useOfVoidInConditionalConditionError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  x ? null : null;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 26, 1),
    ]);
  }

  @failingTest
  test_useOfVoidInConditionalLhsError() async {
    // TODO(mfairhurst) Enable this.
    await assertErrorsInCode('''
void main(bool c) {
  void x;
  c ? x : null;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 36, 1),
    ]);
  }

  @failingTest
  test_useOfVoidInConditionalRhsError() async {
    // TODO(mfairhurst) Enable this.
    await assertErrorsInCode('''
void main(bool c) {
  void x;
  c ? null : x;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 43, 1),
    ]);
  }

  test_useOfVoidInDoWhileConditionError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  do {} while (x);
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 39, 1),
    ]);
  }

  test_useOfVoidInExpStmtOk() async {
    await assertNoErrorsInCode('''
void main() {
  void x;
  x;
}
''');
  }

  @failingTest // This test may be completely invalid.
  test_useOfVoidInForeachVariableError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  for (x in [1, 2]) {}
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 31, 1),
    ]);
  }

  test_useOfVoidInForPartsOk() async {
    await assertNoErrorsInCode('''
void main() {
  void x;
  for (x; false; x) {}
}
''');
  }

  test_useOfVoidInIsTestError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  x is int;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 26, 1),
    ]);
  }

  test_useOfVoidInListLiteralError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  <dynamic>[x];
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 36, 1),
    ]);
  }

  test_useOfVoidInListLiteralOk() async {
    await assertNoErrorsInCode('''
void main() {
  void x;
  <void>[x]; // not strong mode; we have to specify <void>.
}
''');
  }

  test_useOfVoidInMapLiteralKeyError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  var m2 = <dynamic, int>{x : 4};
}
''', [
      error(HintCode.UNUSED_LOCAL_VARIABLE, 30, 2),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 50, 1),
    ]);
  }

  test_useOfVoidInMapLiteralKeyOk() async {
    await assertNoErrorsInCode('''
void main() {
  void x;
  var m2 = <void, int>{x : 4}; // not strong mode; we have to specify <void>.
}
''');
  }

  test_useOfVoidInMapLiteralValueError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  var m1 = <int, dynamic>{4: x};
}
''', [
      error(HintCode.UNUSED_LOCAL_VARIABLE, 30, 2),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 53, 1),
    ]);
  }

  test_useOfVoidInMapLiteralValueOk() async {
    await assertNoErrorsInCode('''
void main() {
  void x;
  var m1 = <int, void>{4: x}; // not strong mode; we have to specify <void>.
}
''');
  }

  test_useOfVoidInNullOperatorLhsError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  x ?? 499;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 26, 1),
    ]);
  }

  test_useOfVoidInNullOperatorRhsOk() async {
    await assertNoErrorsInCode('''
void main() {
  void x;
  null ?? x;
}
''');
  }

  test_useOfVoidInSpecialAssignmentError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  x += 1;
}
''', [
      error(HintCode.UNUSED_LOCAL_VARIABLE, 21, 1),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 28, 2),
    ]);
  }

  test_useOfVoidInSwitchExpressionError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  switch(x) {}
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 33, 1),
    ]);
  }

  test_useOfVoidInWhileConditionError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  while (x) {};
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 33, 1),
    ]);
  }

  test_useOfVoidNullPropertyAccessError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  x?.foo;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 29, 3),
    ]);
  }

  test_useOfVoidPropertyAccessError() async {
    await assertErrorsInCode('''
void main() {
  void x;
  x.foo;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 28, 3),
    ]);
  }

  @failingTest
  test_useOfVoidReturnInNonVoidFunctionError() async {
    // TODO(mfairhurst) Get this test to pass once codebase is compliant.
    await assertErrorsInCode('''
dynamic main() {
  void x;
  return x;
}
''', [
      error(StaticTypeWarningCode.RETURN_OF_INVALID_TYPE, 36, 1),
    ]);
  }

  test_useOfVoidReturnInVoidFunctionOk() async {
    await assertNoErrorsInCode('''
void main() {
  void x;
  return x;
}
''');
  }

  test_useOfVoidWhenArgumentError() async {
    await assertErrorsInCode('''
void use(dynamic x) { }
void main() {
  void x;
  use(x);
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 54, 1),
    ]);
  }

  test_useOfVoidWithInitializerOk() async {
    await assertNoErrorsInCode('''
void main() {
  void x;
  void y = x;
}
''');
  }

  test_variableDeclaration_function_error() async {
    await assertErrorsInCode('''
void f() {}
class A {
  n() {
    Object a = f();
  }
}''', [
      error(HintCode.UNUSED_LOCAL_VARIABLE, 41, 1),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 45, 1),
    ]);
  }

  test_variableDeclaration_function_ok() async {
    await assertNoErrorsInCode('''
void f() {}
class A {
  n() {
    void a = f();
  }
}''');
  }

  test_variableDeclaration_method2() async {
    await assertErrorsInCode('''
class A {
  void m() {}
  n() {
    Object a = m(), b = m();
  }
}''', [
      error(HintCode.UNUSED_LOCAL_VARIABLE, 43, 1),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 47, 1),
      error(HintCode.UNUSED_LOCAL_VARIABLE, 52, 1),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 56, 1),
    ]);
  }

  test_variableDeclaration_method_error() async {
    await assertErrorsInCode('''
class A {
  void m() {}
  n() {
    Object a = m();
  }
}''', [
      error(HintCode.UNUSED_LOCAL_VARIABLE, 43, 1),
      error(StaticWarningCode.USE_OF_VOID_RESULT, 47, 1),
    ]);
  }

  test_variableDeclaration_method_ok() async {
    await assertNoErrorsInCode('''
class A {
  void m() {}
  n() {
    void a = m();
  }
}''');
  }

  test_yieldStarVoid_asyncStar() async {
    await assertErrorsInCode('''
main(void x) async* {
  yield* x;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 31, 1),
    ]);
  }

  test_yieldStarVoid_syncStar() async {
    await assertErrorsInCode('''
main(void x) sync* {
  yield* x;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 30, 1),
    ]);
  }

  test_yieldVoid_asyncStar() async {
    await assertErrorsInCode('''
main(void x) async* {
  yield x;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 30, 1),
    ]);
  }

  test_yieldVoid_syncStar() async {
    await assertErrorsInCode('''
main(void x) sync* {
  yield x;
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 29, 1),
    ]);
  }
}

@reflectiveTest
class UseOfVoidResultTest_NonNullable extends DriverResolutionTest {
  @override
  AnalysisOptionsImpl get analysisOptions =>
      AnalysisOptionsImpl()..enabledExperiments = [EnableString.non_nullable];

  test_bang_nonVoid() async {
    await assertNoErrorsInCode(r'''
int? f() => 1;
g() {
  f()!;
}
''');
  }

  test_bang_void() async {
    await assertErrorsInCode(r'''
void f() => 1;
g() {
  f()!;
}
''', [ExpectedError(StaticWarningCode.USE_OF_VOID_RESULT, 23, 4)]);
  }
}

@reflectiveTest
class UseOfVoidResultWithExtensionMethodsTest extends UseOfVoidResultTest {
  @override
  AnalysisOptionsImpl get analysisOptions => AnalysisOptionsImpl()
    ..contextFeatures = FeatureSet.forTesting(
        sdkVersion: '2.3.0', additionalFeatures: [Feature.extension_methods]);

  test_useOfVoidReturnInExtensionMethod() async {
    await assertErrorsInCode('''
extension on void {
  testVoid() {
    // No access on void. Static type of `this` is void!
    this.toString();
  }
}
''', [
      error(StaticWarningCode.USE_OF_VOID_RESULT, 96, 4),
    ]);
  }
}
