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

library analyzer.test.src.task.incremental_element_builder_test;

import 'package:analyzer/dart/ast/ast.dart';
import 'package:analyzer/dart/element/element.dart';
import 'package:analyzer/dart/element/visitor.dart';
import 'package:analyzer/src/dart/ast/utilities.dart';
import 'package:analyzer/src/dart/element/element.dart';
import 'package:analyzer/src/generated/engine.dart';
import 'package:analyzer/src/generated/source.dart';
import 'package:analyzer/src/task/dart.dart';
import 'package:analyzer/src/task/incremental_element_builder.dart';
import 'package:analyzer/task/dart.dart';
import 'package:unittest/unittest.dart';

import '../../reflective_tests.dart';
import '../../utils.dart';
import '../context/abstract_context.dart';

main() {
  initializeTestEnvironment();
  runReflectiveTests(IncrementalCompilationUnitElementBuilderTest);
}

@reflectiveTest
class IncrementalCompilationUnitElementBuilderTest extends AbstractContextTest {
  Source source;

  String oldCode;
  CompilationUnit oldUnit;
  CompilationUnitElement unitElement;

  String newCode;
  CompilationUnit newUnit;

  CompilationUnitElementDelta unitDelta;

  String getNodeText(AstNode node) {
    return newCode.substring(node.offset, node.end);
  }

  test_classDelta_constructor_0to1() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
}
''');
    helper.initOld(oldUnit);
    ConstructorElement oldConstructorElement =
        helper.element.unnamedConstructor;
    _buildNewUnit(r'''
class A {
  A.a();
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    ClassMember newConstructorNode = helper.newMembers[0];
    // elements
    ConstructorElement newConstructorElement = newConstructorNode.element;
    expect(newConstructorElement, isNotNull);
    expect(newConstructorElement.name, 'a');
    // classElement.constructors
    ClassElement classElement = helper.element;
    expect(classElement.constructors, unorderedEquals([newConstructorElement]));
    // verify delta
    expect(helper.delta.hasUnnamedConstructorChange, isTrue);
    expect(helper.delta.addedConstructors,
        unorderedEquals([newConstructorElement]));
    expect(helper.delta.removedConstructors,
        unorderedEquals([oldConstructorElement]));
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_constructor_1to0() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  A.a();
}
''');
    helper.initOld(oldUnit);
    ConstructorElement oldElementA = helper.element.getNamedConstructor('a');
    _buildNewUnit(r'''
class A {
}
''');
    helper.initNew(newUnit, unitDelta);
    // classElement.constructors
    ClassElement classElement = helper.element;
    {
      List<ConstructorElement> constructors = classElement.constructors;
      expect(constructors, hasLength(1));
      expect(constructors[0].isDefaultConstructor, isTrue);
      expect(constructors[0].isSynthetic, isTrue);
    }
    // verify delta
    expect(helper.delta.hasUnnamedConstructorChange, isTrue);
    expect(helper.delta.addedConstructors,
        unorderedEquals([classElement.unnamedConstructor]));
    expect(helper.delta.removedConstructors, unorderedEquals([oldElementA]));
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_constructor_1to1_unnamed_addParameter() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  A();
}
''');
    helper.initOld(oldUnit);
    ConstructorElement oldConstructor = helper.element.unnamedConstructor;
    _buildNewUnit(r'''
class A {
  A(int p);
}
''');
    helper.initNew(newUnit, unitDelta);
    ClassElement classElement = helper.element;
    ConstructorElement newConstructor = classElement.unnamedConstructor;
    expect(classElement.constructors, [newConstructor]);
    // verify delta
    expect(helper.delta.hasUnnamedConstructorChange, isTrue);
    expect(helper.delta.addedConstructors, unorderedEquals([newConstructor]));
    expect(helper.delta.removedConstructors, unorderedEquals([oldConstructor]));
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_constructor_1to1_unnamed_removeParameter() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  final int a;
  final int b;
  A(this.a, this.b);
}
''');
    helper.initOld(oldUnit);
    ConstructorElement oldConstructor = helper.element.unnamedConstructor;
    _buildNewUnit(r'''
class A {
  final int a;
  final int b;
  A(this.a);
}
''');
    helper.initNew(newUnit, unitDelta);
    ClassElement classElement = helper.element;
    ConstructorElement newConstructor = classElement.unnamedConstructor;
    expect(classElement.constructors, [newConstructor]);
    // verify delta
    expect(helper.delta.hasUnnamedConstructorChange, isTrue);
    expect(helper.delta.addedConstructors, unorderedEquals([newConstructor]));
    expect(helper.delta.removedConstructors, unorderedEquals([oldConstructor]));
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_constructor_1to2() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  A.a();
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  A.a();
  A.b();
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    ClassMember nodeA = helper.newMembers[0];
    ClassMember nodeB = helper.newMembers[1];
    expect(nodeA, same(helper.oldMembers[0]));
    // elements
    ConstructorElement elementA = nodeA.element;
    ConstructorElement elementB = nodeB.element;
    expect(elementA, isNotNull);
    expect(elementB, isNotNull);
    expect(elementA.name, 'a');
    expect(elementB.name, 'b');
    // classElement.constructors
    ClassElement classElement = helper.element;
    expect(classElement.constructors, unorderedEquals([elementA, elementB]));
    // verify delta
    expect(helper.delta.addedConstructors, unorderedEquals([elementB]));
    expect(helper.delta.removedConstructors, unorderedEquals([]));
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_constructor_2to1() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  A.a();
  A.b();
}
''');
    helper.initOld(oldUnit);
    ConstructorElement oldElementA = helper.element.getNamedConstructor('a');
    _buildNewUnit(r'''
class A {
  A.b();
}
''');
    helper.initNew(newUnit, unitDelta);
    expect(helper.delta.hasUnnamedConstructorChange, isFalse);
    // nodes
    ClassMember nodeB = helper.newMembers[0];
    expect(nodeB, same(helper.oldMembers[1]));
    // elements
    ConstructorElement elementB = nodeB.element;
    expect(elementB, isNotNull);
    expect(elementB.name, 'b');
    // classElement.constructors
    ClassElement classElement = helper.element;
    expect(classElement.constructors, unorderedEquals([elementB]));
    // verify delta
    expect(helper.delta.addedConstructors, unorderedEquals([]));
    expect(helper.delta.removedConstructors, unorderedEquals([oldElementA]));
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_constructor_2to2_reorder() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  A.a();
  A.b();
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  A.b();
  A.a();
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    ClassMember nodeB = helper.newMembers[0];
    ClassMember nodeA = helper.newMembers[1];
    expect(nodeB, same(helper.oldMembers[1]));
    expect(nodeA, same(helper.oldMembers[0]));
    // elements
    ConstructorElement elementB = nodeB.element;
    ConstructorElement elementA = nodeA.element;
    expect(elementB, isNotNull);
    expect(elementA, isNotNull);
    expect(elementB.name, 'b');
    expect(elementA.name, 'a');
    // classElement.constructors
    ClassElement classElement = helper.element;
    expect(classElement.constructors, unorderedEquals([elementB, elementA]));
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_constructor_fieldReference_initializer() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  final int f;
  A() : f = 1 {}
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  final int f;
  A() : f = 1;
}
''');
    helper.initNew(newUnit, unitDelta);
  }

  test_classDelta_constructor_fieldReference_parameter() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  final int f;
  A(this.f) {}
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  final int f;
  A(this.f);
}
''');
    helper.initNew(newUnit, unitDelta);
  }

  test_classDelta_constructor_fieldReference_parameter_default() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  final int f;
  A([this.f = 1]) {}
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  final int f;
  A([this.f = 1]);
}
''');
    helper.initNew(newUnit, unitDelta);
  }

  test_classDelta_duplicate_constructor() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  A() {}
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  A() {}
  A() {}
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    ConstructorDeclaration oldNode = helper.oldMembers[0];
    ConstructorDeclaration newNode1 = helper.newMembers[0];
    ConstructorDeclaration newNode2 = helper.newMembers[1];
    // elements
    ConstructorElement oldElement = oldNode.element;
    ConstructorElement newElement1 = newNode1.element;
    ConstructorElement newElement2 = newNode2.element;
    expect(newElement1, same(oldElement));
    expect(newElement2, isNot(same(oldElement)));
    expect(oldElement.name, '');
    expect(newElement1.name, '');
    expect(newElement2.name, '');
    // verify delta
    expect(helper.delta.addedConstructors, unorderedEquals([newElement2]));
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_duplicate_method() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  m() {}
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  m() {}
  m() {}
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    MethodDeclaration oldNode = helper.oldMembers[0];
    MethodDeclaration newNode1 = helper.newMembers[0];
    MethodDeclaration newNode2 = helper.newMembers[1];
    // elements
    MethodElement oldElement = oldNode.element;
    MethodElement newElement1 = newNode1.element;
    MethodElement newElement2 = newNode2.element;
    expect(newElement1, same(oldElement));
    expect(newElement2, isNot(same(oldElement)));
    expect(oldElement.name, 'm');
    expect(newElement1.name, 'm');
    expect(newElement2.name, 'm');
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, unorderedEquals([newElement2]));
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_field_add() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  int aaa;
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  int aaa;
  int bbb;
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    FieldDeclaration nodeA = helper.newMembers[0];
    FieldDeclaration newNodeB = helper.newMembers[1];
    List<VariableDeclaration> newFieldsB = newNodeB.fields.variables;
    expect(nodeA, same(helper.oldMembers[0]));
    expect(newFieldsB, hasLength(1));
    // elements
    FieldElement newFieldElementB = newFieldsB[0].name.staticElement;
    expect(newFieldElementB.name, 'bbb');
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors,
        unorderedEquals([newFieldElementB.getter, newFieldElementB.setter]));
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_field_remove() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  int aaa;
  int bbb;
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  int aaa;
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    FieldDeclaration nodeA = helper.newMembers[0];
    FieldDeclaration oldNodeB = helper.oldMembers[1];
    List<VariableDeclaration> oldFieldsB = oldNodeB.fields.variables;
    expect(nodeA, same(helper.oldMembers[0]));
    // elements
    FieldElement oldFieldElementB = oldFieldsB[0].name.staticElement;
    expect(oldFieldElementB.name, 'bbb');
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors,
        unorderedEquals([oldFieldElementB.getter, oldFieldElementB.setter]));
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_getter_add() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  int get aaa => 1;
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  int get aaa => 1;
  int get bbb => 2;
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    MethodDeclaration nodeA = helper.oldMembers[0];
    MethodDeclaration newNodeB = helper.newMembers[1];
    expect(nodeA, same(helper.oldMembers[0]));
    // elements
    PropertyAccessorElement elementA = nodeA.element;
    PropertyAccessorElement newElementB = newNodeB.element;
    expect(elementA, isNotNull);
    expect(elementA.name, 'aaa');
    expect(newElementB, isNotNull);
    expect(newElementB.name, 'bbb');
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, unorderedEquals([newElementB]));
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_getter_remove() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  int get aaa => 1;
  int get bbb => 2;
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  int get aaa => 1;
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    MethodDeclaration nodeA = helper.oldMembers[0];
    MethodDeclaration oldNodeB = helper.oldMembers[1];
    expect(nodeA, same(helper.oldMembers[0]));
    // elements
    PropertyAccessorElement elementA = nodeA.element;
    PropertyAccessorElement oldElementB = oldNodeB.element;
    expect(elementA, isNotNull);
    expect(elementA.name, 'aaa');
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, unorderedEquals([oldElementB]));
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_method_add() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  aaa() {}
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  aaa() {}
  bbb() {}
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    ClassMember nodeA = helper.oldMembers[0];
    ClassMember newNodeB = helper.newMembers[1];
    expect(nodeA, same(helper.oldMembers[0]));
    // elements
    MethodElement elementA = nodeA.element;
    MethodElement newElementB = newNodeB.element;
    expect(elementA, isNotNull);
    expect(elementA.name, 'aaa');
    expect(newElementB, isNotNull);
    expect(newElementB.name, 'bbb');
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, unorderedEquals([newElementB]));
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_method_addParameter() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  aaa() {}
  bbb() {}
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  aaa(int p) {}
  bbb() {}
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    ClassMember oldNodeA = helper.oldMembers[0];
    ClassMember newNodeA = helper.newMembers[0];
    ClassMember nodeB = helper.newMembers[1];
    expect(newNodeA, isNot(same(oldNodeA)));
    expect(nodeB, same(helper.oldMembers[1]));
    // elements
    MethodElement oldElementA = oldNodeA.element;
    MethodElement newElementA = newNodeA.element;
    MethodElement elementB = nodeB.element;
    expect(newElementA, isNotNull);
    expect(newElementA.name, 'aaa');
    expect(oldElementA.parameters, hasLength(0));
    expect(newElementA.parameters, hasLength(1));
    expect(elementB, isNotNull);
    expect(elementB.name, 'bbb');
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, unorderedEquals([newElementA]));
    expect(helper.delta.removedMethods, unorderedEquals([oldElementA]));
  }

  test_classDelta_method_changeName() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  aaa(int ap) {
    int av = 1;
    af(afp) {}
  }
  bbb(int bp) {
    int bv = 1;
    bf(bfp) {}
  }
}
''');
    helper.initOld(oldUnit);
    ConstructorElement oldConstructor = helper.element.unnamedConstructor;
    _buildNewUnit(r'''
class A {
  aaa2(int ap) {
    int av = 1;
    af(afp) {}
  }
  bbb(int bp) {
    int bv = 1;
    bf(bfp) {}
  }
}
''');
    helper.initNew(newUnit, unitDelta);
    expect(helper.element.unnamedConstructor, same(oldConstructor));
    // nodes
    ClassMember oldNodeA = helper.oldMembers[0];
    ClassMember newNodeA = helper.newMembers[0];
    ClassMember nodeB = helper.newMembers[1];
    expect(nodeB, same(helper.oldMembers[1]));
    // elements
    MethodElement oldElementA = oldNodeA.element;
    MethodElement newElementA = newNodeA.element;
    MethodElement elementB = nodeB.element;
    expect(newElementA, isNotNull);
    expect(newElementA.name, 'aaa2');
    expect(elementB, isNotNull);
    expect(elementB.name, 'bbb');
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, unorderedEquals([newElementA]));
    expect(helper.delta.removedMethods, unorderedEquals([oldElementA]));
  }

  test_classDelta_method_remove() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  aaa() {}
  bbb() {}
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  aaa() {}
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    ClassMember nodeA = helper.oldMembers[0];
    ClassMember oldNodeB = helper.oldMembers[1];
    expect(nodeA, same(helper.oldMembers[0]));
    // elements
    MethodElement elementA = nodeA.element;
    MethodElement oldElementB = oldNodeB.element;
    expect(elementA, isNotNull);
    expect(elementA.name, 'aaa');
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, unorderedEquals([oldElementB]));
  }

  test_classDelta_method_removeParameter() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  aaa(int p) {}
  bbb() {}
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  aaa() {}
  bbb() {}
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    ClassMember oldNodeA = helper.oldMembers[0];
    ClassMember newNodeA = helper.newMembers[0];
    ClassMember nodeB = helper.newMembers[1];
    expect(newNodeA, isNot(same(oldNodeA)));
    expect(nodeB, same(helper.oldMembers[1]));
    // elements
    MethodElement oldElementA = oldNodeA.element;
    MethodElement newElementA = newNodeA.element;
    MethodElement elementB = nodeB.element;
    expect(newElementA, isNotNull);
    expect(newElementA.name, 'aaa');
    expect(oldElementA.parameters, hasLength(1));
    expect(newElementA.parameters, hasLength(0));
    expect(elementB, isNotNull);
    expect(elementB.name, 'bbb');
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, unorderedEquals([newElementA]));
    expect(helper.delta.removedMethods, unorderedEquals([oldElementA]));
  }

  test_classDelta_null_abstractKeyword_add() {
    _verifyNoClassDeltaForTheLast(
        r'''
class A {}
''',
        r'''
abstract class A {}
''');
  }

  test_classDelta_null_abstractKeyword_remove() {
    _verifyNoClassDeltaForTheLast(
        r'''
abstract class A {}
''',
        r'''
class A {}
''');
  }

  test_classDelta_null_extendsClause_add() {
    _verifyNoClassDeltaForTheLast(
        r'''
class A {}
class B {}
''',
        r'''
class A {}
class B extends A {}
''');
  }

  test_classDelta_null_extendsClause_change() {
    _verifyNoClassDeltaForTheLast(
        r'''
class A1 {}
class A2 {}
class B extends A1 {}
''',
        r'''
class A1 {}
class A2 {}
class B extends A2 {}
''');
  }

  test_classDelta_null_extendsClause_remove() {
    _verifyNoClassDeltaForTheLast(
        r'''
class A {}
class B extends A {}
''',
        r'''
class A {}
class B {}
''');
  }

  test_classDelta_null_implementsClause_add() {
    _verifyNoClassDeltaForTheLast(
        r'''
class A {}
class B {}
''',
        r'''
class A {}
class B implements A {}
''');
  }

  test_classDelta_null_implementsClause_change() {
    _verifyNoClassDeltaForTheLast(
        r'''
class A1 {}
class A2 {}
class B implements A1 {}
''',
        r'''
class A1 {}
class A2 {}
class B implements A2 {}
''');
  }

  test_classDelta_null_implementsClause_remove() {
    _verifyNoClassDeltaForTheLast(
        r'''
class A {}
class B implements A {}
''',
        r'''
class A {}
class B {}
''');
  }

  test_classDelta_null_typeParameters_change() {
    _verifyNoClassDeltaForTheLast(
        r'''
class A {}
class B<T> {}
''',
        r'''
class A {}
class B<T extends A> {}
''');
  }

  test_classDelta_null_withClause_add() {
    _verifyNoClassDeltaForTheLast(
        r'''
class A {}
class M {}
class B extends A {}
''',
        r'''
class A {}
class M {}
class B extends A with M {}
''');
  }

  test_classDelta_null_withClause_change1() {
    _verifyNoClassDeltaForTheLast(
        r'''
class A {}
class M1 {}
class M2 {}
class B extends A with M1 {}
''',
        r'''
class A {}
class M1 {}
class M2 {}
class B extends A with M2 {}
''');
  }

  test_classDelta_null_withClause_change2() {
    _verifyNoClassDeltaForTheLast(
        r'''
class A {}
class M1 {}
class M2 {}
class B extends A with M1, M2 {}
''',
        r'''
class A {}
class M1 {}
class M2 {}
class B extends A with M2, M1 {}
''');
  }

  test_classDelta_null_withClause_remove() {
    _verifyNoClassDeltaForTheLast(
        r'''
class A {}
class M {}
class B extends A with M {}
''',
        r'''
class A {}
class M {}
class B extends A {}
''');
  }

  test_classDelta_setter_add() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  void set aaa(int pa) {}
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  void set aaa(int pa) {}
  void set bbb(int pb) {}
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    MethodDeclaration nodeA = helper.oldMembers[0];
    MethodDeclaration newNodeB = helper.newMembers[1];
    expect(nodeA, same(helper.oldMembers[0]));
    // elements
    PropertyAccessorElement elementA = nodeA.element;
    PropertyAccessorElement newElementB = newNodeB.element;
    expect(elementA, isNotNull);
    expect(elementA.name, 'aaa=');
    expect(newElementB, isNotNull);
    expect(newElementB.name, 'bbb=');
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, unorderedEquals([newElementB]));
    expect(helper.delta.removedAccessors, isEmpty);
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_setter_remove() {
    var helper = new _ClassDeltaHelper('A');
    _buildOldUnit(r'''
class A {
  void set aaa(int pa) {}
  void set bbb(int pb) {}
}
''');
    helper.initOld(oldUnit);
    _buildNewUnit(r'''
class A {
  void set aaa(int pa) {}
}
''');
    helper.initNew(newUnit, unitDelta);
    // nodes
    MethodDeclaration nodeA = helper.oldMembers[0];
    MethodDeclaration oldNodeB = helper.oldMembers[1];
    expect(nodeA, same(helper.oldMembers[0]));
    // elements
    PropertyAccessorElement elementA = nodeA.element;
    PropertyAccessorElement oldElementB = oldNodeB.element;
    expect(elementA, isNotNull);
    expect(elementA.name, 'aaa=');
    // verify delta
    expect(helper.delta.addedConstructors, isEmpty);
    expect(helper.delta.removedConstructors, isEmpty);
    expect(helper.delta.addedAccessors, isEmpty);
    expect(helper.delta.removedAccessors, unorderedEquals([oldElementB]));
    expect(helper.delta.addedMethods, isEmpty);
    expect(helper.delta.removedMethods, isEmpty);
  }

  test_classDelta_typeParameter_same() {
    _buildOldUnit(r'''
class A<T> {
  m() {}
}
''');
    _buildNewUnit(r'''
class A<T> {
  m2() {}
}
''');
  }

  test_directives_add() {
    _buildOldUnit(r'''
library test;
import 'dart:math';
''');
    List<Directive> oldDirectives = oldUnit.directives.toList();
    _buildNewUnit(r'''
library test;
import 'dart:async';
import 'dart:math';
''');
    List<Directive> newDirectives = newUnit.directives;
    {
      Directive newNode = newDirectives[0];
      expect(newNode, same(oldDirectives[0]));
      expect(getNodeText(newNode), "library test;");
      LibraryElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf('test;'));
    }
    {
      Directive newNode = newDirectives[1];
      expect(getNodeText(newNode), "import 'dart:async';");
      ImportElement element = newNode.element;
      expect(element, isNull);
    }
    {
      Directive newNode = newDirectives[2];
      expect(newNode, same(oldDirectives[1]));
      expect(getNodeText(newNode), "import 'dart:math';");
      ImportElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf("import 'dart:math';"));
    }
    expect(unitDelta.hasDirectiveChange, isTrue);
  }

  test_directives_keepOffset_partOf() {
    String libCode = '''
// comment to shift tokens
library my_lib;
part 'test.dart';
''';
    Source libSource = newSource('/lib.dart', libCode);
    _buildOldUnit(
        r'''
part of my_lib;
class A {}
''',
        libSource);
    List<Directive> oldDirectives = oldUnit.directives.toList();
    _buildNewUnit(r'''
part of my_lib;
class A {}
''');
    List<Directive> newDirectives = newUnit.directives;
    {
      Directive newNode = newDirectives[0];
      expect(newNode, same(oldDirectives[0]));
      expect(getNodeText(newNode), 'part of my_lib;');
      LibraryElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, libCode.indexOf('my_lib;'));
    }
  }

  test_directives_library_updateOffset() {
    _buildOldUnit(r'''
#!/bin/sh
library my_lib;
class A {}
''');
    LibraryDirective libraryDirective = oldUnit.directives.single;
    // Set the LibraryElement and check that its nameOffset is correct.
    libraryDirective.element =
        new LibraryElementImpl.forNode(context, libraryDirective.name);
    expect(libraryDirective.element.nameOffset, libraryDirective.name.offset);
    // Update and check again that the nameOffset is correct.
    _buildNewUnit(r'''
#!/bin/sh

library my_lib;
class A {}
''');
    expect(libraryDirective.element.nameOffset, libraryDirective.name.offset);
  }

  test_directives_remove() {
    _buildOldUnit(r'''
library test;
import 'dart:async';
import 'dart:math';
''');
    List<Directive> oldDirectives = oldUnit.directives.toList();
    _buildNewUnit(r'''
library test;
import 'dart:math';
''');
    List<Directive> newDirectives = newUnit.directives;
    {
      Directive newNode = newDirectives[0];
      expect(newNode, same(oldDirectives[0]));
      expect(getNodeText(newNode), "library test;");
      LibraryElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf('test;'));
    }
    {
      Directive newNode = newDirectives[1];
      expect(newNode, same(oldDirectives[2]));
      expect(getNodeText(newNode), "import 'dart:math';");
      ImportElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf("import 'dart:math';"));
    }
    expect(unitDelta.hasDirectiveChange, isTrue);
  }

  test_directives_reorder() {
    _buildOldUnit(r'''
library test;
import  'dart:math' as m;
import 'dart:async';
''');
    List<Directive> oldDirectives = oldUnit.directives.toList();
    _buildNewUnit(r'''
library test;
import 'dart:async';
import 'dart:math' as m;
''');
    List<Directive> newDirectives = newUnit.directives;
    {
      Directive newNode = newDirectives[0];
      expect(newNode, same(oldDirectives[0]));
      expect(getNodeText(newNode), "library test;");
      LibraryElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf('test;'));
    }
    {
      Directive newNode = newDirectives[1];
      expect(newNode, same(oldDirectives[2]));
      expect(getNodeText(newNode), "import 'dart:async';");
      ImportElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf("import 'dart:async';"));
    }
    {
      Directive newNode = newDirectives[2];
      expect(newNode, same(oldDirectives[1]));
      expect(getNodeText(newNode), "import 'dart:math' as m;");
      ImportElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf("import 'dart:math' as m;"));
      expect(element.prefix.nameOffset, newCode.indexOf("m;"));
    }
    expect(unitDelta.hasDirectiveChange, isFalse);
  }

  test_directives_sameOrder_insertSpaces() {
    _buildOldUnit(r'''
library test;
import 'dart:async';
import 'dart:math';
''');
    List<Directive> oldDirectives = oldUnit.directives.toList();
    _buildNewUnit(r'''
library test;

import 'dart:async' ;
import  'dart:math';
''');
    List<Directive> newDirectives = newUnit.directives;
    {
      Directive newNode = newDirectives[0];
      expect(newNode, same(oldDirectives[0]));
      expect(getNodeText(newNode), "library test;");
      LibraryElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf('test;'));
    }
    {
      Directive newNode = newDirectives[1];
      expect(newNode, same(oldDirectives[1]));
      expect(getNodeText(newNode), "import 'dart:async' ;");
      ImportElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf("import 'dart:async' ;"));
    }
    {
      Directive newNode = newDirectives[2];
      expect(newNode, same(oldDirectives[2]));
      expect(getNodeText(newNode), "import  'dart:math';");
      ImportElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf("import  'dart:math';"));
    }
    expect(unitDelta.hasDirectiveChange, isFalse);
  }

  test_directives_sameOrder_removeSpaces() {
    _buildOldUnit(r'''
library test;

import 'dart:async' ;
import  'dart:math';
''');
    List<Directive> oldDirectives = oldUnit.directives.toList();
    _buildNewUnit(r'''
library test;
import 'dart:async';
import 'dart:math';
''');
    List<Directive> newDirectives = newUnit.directives;
    {
      Directive newNode = newDirectives[0];
      expect(newNode, same(oldDirectives[0]));
      expect(getNodeText(newNode), "library test;");
      LibraryElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf('test;'));
    }
    {
      Directive newNode = newDirectives[1];
      expect(newNode, same(oldDirectives[1]));
      expect(getNodeText(newNode), "import 'dart:async';");
      ImportElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf("import 'dart:async';"));
    }
    {
      Directive newNode = newDirectives[2];
      expect(newNode, same(oldDirectives[2]));
      expect(getNodeText(newNode), "import 'dart:math';");
      ImportElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.nameOffset, newCode.indexOf("import 'dart:math';"));
    }
    expect(unitDelta.hasDirectiveChange, isFalse);
  }

  test_unitMembers_accessor_add() {
    _buildOldUnit(r'''
get a => 1;
''');
    List<CompilationUnitMember> oldNodes = oldUnit.declarations.toList();
    _buildNewUnit(r'''
get a => 1;
get b => 2;
''');
    List<CompilationUnitMember> newNodes = newUnit.declarations;
    // nodes
    FunctionDeclaration node1 = newNodes[0];
    FunctionDeclaration node2 = newNodes[1];
    expect(node1, same(oldNodes[0]));
    // elements
    PropertyAccessorElement elementA = node1.element;
    PropertyAccessorElement elementB = node2.element;
    expect(elementA, isNotNull);
    expect(elementB, isNotNull);
    expect(elementA.name, 'a');
    expect(elementB.name, 'b');
    // unit.types
    expect(unitElement.topLevelVariables,
        unorderedEquals([elementA.variable, elementB.variable]));
    expect(unitElement.accessors, unorderedEquals([elementA, elementB]));
  }

  test_unitMembers_class_add() {
    _buildOldUnit(r'''
class A {}
''');
    List<CompilationUnitMember> oldNodes = oldUnit.declarations.toList();
    _buildNewUnit(r'''
class A {}
class B {}
''');
    List<CompilationUnitMember> newNodes = newUnit.declarations;
    // nodes
    CompilationUnitMember nodeA = newNodes[0];
    CompilationUnitMember nodeB = newNodes[1];
    expect(nodeA, same(oldNodes[0]));
    // elements
    ClassElement elementA = nodeA.element;
    ClassElement elementB = nodeB.element;
    expect(elementA, isNotNull);
    expect(elementB, isNotNull);
    expect(elementA.name, 'A');
    expect(elementB.name, 'B');
    // unit.types
    expect(unitElement.types, unorderedEquals([elementA, elementB]));
    // verify delta
    expect(unitDelta.addedDeclarations, unorderedEquals([elementB]));
    expect(unitDelta.removedDeclarations, unorderedEquals([]));
  }

  test_unitMembers_class_comments() {
    _buildOldUnit(r'''
/// reference [bool] type.
class A {}
/// reference [int] type.
class B {}
/// reference [double] and [B] types.
class C {}
''');
    List<CompilationUnitMember> oldNodes = oldUnit.declarations.toList();
    _buildNewUnit(r'''
/// reference [double] and [B] types.
class C {}
/// reference [bool] type.
class A {}
/// reference [int] type.
class B {}
''');
    List<CompilationUnitMember> newNodes = newUnit.declarations;
    {
      CompilationUnitMember newNode = newNodes[0];
      expect(newNode, same(oldNodes[2]));
      expect(
          getNodeText(newNode),
          r'''
/// reference [double] and [B] types.
class C {}''');
      ClassElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.name, 'C');
      expect(element.nameOffset, newCode.indexOf('C {}'));
      // [double] and [B] are still resolved
      {
        var docReferences = newNode.documentationComment.references;
        expect(docReferences, hasLength(2));
        expect(docReferences[0].identifier.staticElement.name, 'double');
        expect(docReferences[1].identifier.staticElement,
            same(newNodes[2].element));
      }
    }
    {
      CompilationUnitMember newNode = newNodes[1];
      expect(newNode, same(oldNodes[0]));
      expect(
          getNodeText(newNode),
          r'''
/// reference [bool] type.
class A {}''');
      ClassElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.name, 'A');
      expect(element.nameOffset, newCode.indexOf('A {}'));
      // [bool] is still resolved
      {
        var docReferences = newNode.documentationComment.references;
        expect(docReferences, hasLength(1));
        expect(docReferences[0].identifier.staticElement.name, 'bool');
      }
    }
    {
      CompilationUnitMember newNode = newNodes[2];
      expect(newNode, same(oldNodes[1]));
      expect(
          getNodeText(newNode),
          r'''
/// reference [int] type.
class B {}''');
      ClassElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.name, 'B');
      expect(element.nameOffset, newCode.indexOf('B {}'));
      // [int] is still resolved
      {
        var docReferences = newNode.documentationComment.references;
        expect(docReferences, hasLength(1));
        expect(docReferences[0].identifier.staticElement.name, 'int');
      }
    }
    // verify delta
    expect(unitDelta.addedDeclarations, unorderedEquals([]));
    expect(unitDelta.removedDeclarations, unorderedEquals([]));
  }

  test_unitMembers_class_remove() {
    _buildOldUnit(r'''
class A {}
class B {}
''');
    List<CompilationUnitMember> oldNodes = oldUnit.declarations.toList();
    _buildNewUnit(r'''
class A {}
''');
    List<CompilationUnitMember> newNodes = newUnit.declarations;
    // nodes
    CompilationUnitMember nodeA = newNodes[0];
    CompilationUnitMember nodeB = oldNodes[1];
    expect(nodeA, same(oldNodes[0]));
    // elements
    ClassElement elementA = nodeA.element;
    ClassElement elementB = nodeB.element;
    expect(elementA, isNotNull);
    expect(elementB, isNotNull);
    expect(elementA.name, 'A');
    expect(elementB.name, 'B');
    // unit.types
    expect(unitElement.types, unorderedEquals([elementA]));
    // verify delta
    expect(unitDelta.addedDeclarations, unorderedEquals([]));
    expect(unitDelta.removedDeclarations, unorderedEquals([elementB]));
  }

  test_unitMembers_class_reorder() {
    _buildOldUnit(r'''
class A {}
class B {}
class C {}
''');
    List<CompilationUnitMember> oldNodes = oldUnit.declarations.toList();
    _buildNewUnit(r'''
class C {}
class A {}
class B {}
''');
    List<CompilationUnitMember> newNodes = newUnit.declarations;
    {
      CompilationUnitMember newNode = newNodes[0];
      expect(newNode, same(oldNodes[2]));
      expect(getNodeText(newNode), 'class C {}');
      ClassElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.name, 'C');
      expect(element.nameOffset, newCode.indexOf('C {}'));
    }
    {
      CompilationUnitMember newNode = newNodes[1];
      expect(newNode, same(oldNodes[0]));
      expect(getNodeText(newNode), 'class A {}');
      ClassElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.name, 'A');
      expect(element.nameOffset, newCode.indexOf('A {}'));
    }
    {
      CompilationUnitMember newNode = newNodes[2];
      expect(newNode, same(oldNodes[1]));
      expect(getNodeText(newNode), 'class B {}');
      ClassElement element = newNode.element;
      expect(element, isNotNull);
      expect(element.name, 'B');
      expect(element.nameOffset, newCode.indexOf('B {}'));
    }
    // verify delta
    expect(unitDelta.addedDeclarations, unorderedEquals([]));
    expect(unitDelta.removedDeclarations, unorderedEquals([]));
  }

  test_unitMembers_enum_add() {
    _buildOldUnit(r'''
enum A {A1, A2}
''');
    List<CompilationUnitMember> oldNodes = oldUnit.declarations.toList();
    _buildNewUnit(r'''
enum A {A1, A2}
enum B {B1, B2}
''');
    List<CompilationUnitMember> newNodes = newUnit.declarations;
    // nodes
    CompilationUnitMember nodeA = newNodes[0];
    CompilationUnitMember nodeB = newNodes[1];
    expect(nodeA, same(oldNodes[0]));
    // elements
    ClassElement elementA = nodeA.element;
    ClassElement elementB = nodeB.element;
    expect(elementA, isNotNull);
    expect(elementB, isNotNull);
    expect(elementA.name, 'A');
    expect(elementB.name, 'B');
    expect(elementA.fields.map((f) => f.name),
        unorderedEquals(['index', 'values', 'A1', 'A2']));
    expect(elementA.accessors.map((a) => a.name),
        unorderedEquals(['index', 'values', 'A1', 'A2']));
    expect(elementB.fields.map((f) => f.name),
        unorderedEquals(['index', 'values', 'B1', 'B2']));
    expect(elementB.accessors.map((a) => a.name),
        unorderedEquals(['index', 'values', 'B1', 'B2']));
    // unit.types
    expect(unitElement.enums, unorderedEquals([elementA, elementB]));
    // verify delta
    expect(unitDelta.addedDeclarations, unorderedEquals([elementB]));
    expect(unitDelta.removedDeclarations, unorderedEquals([]));
  }

  test_unitMembers_function_add() {
    _buildOldUnit(r'''
a() {}
''');
    List<CompilationUnitMember> oldNodes = oldUnit.declarations.toList();
    _buildNewUnit(r'''
a() {}
b() {}
''');
    List<CompilationUnitMember> newNodes = newUnit.declarations;
    // nodes
    CompilationUnitMember nodeA = newNodes[0];
    CompilationUnitMember nodeB = newNodes[1];
    expect(nodeA, same(oldNodes[0]));
    // elements
    FunctionElement elementA = nodeA.element;
    FunctionElement elementB = nodeB.element;
    expect(elementA, isNotNull);
    expect(elementB, isNotNull);
    expect(elementA.name, 'a');
    expect(elementB.name, 'b');
    // unit.types
    expect(unitElement.functions, unorderedEquals([elementA, elementB]));
    // verify delta
    expect(unitDelta.addedDeclarations, unorderedEquals([elementB]));
    expect(unitDelta.removedDeclarations, unorderedEquals([]));
  }

  test_unitMembers_functionTypeAlias_add() {
    _buildOldUnit(r'''
typedef A();
''');
    List<CompilationUnitMember> oldNodes = oldUnit.declarations.toList();
    _buildNewUnit(r'''
typedef A();
typedef B();
''');
    List<CompilationUnitMember> newNodes = newUnit.declarations;
    // nodes
    CompilationUnitMember nodeA = newNodes[0];
    CompilationUnitMember nodeB = newNodes[1];
    expect(nodeA, same(oldNodes[0]));
    // elements
    FunctionTypeAliasElement elementA = nodeA.element;
    FunctionTypeAliasElement elementB = nodeB.element;
    expect(elementA, isNotNull);
    expect(elementB, isNotNull);
    expect(elementA.name, 'A');
    expect(elementB.name, 'B');
    // unit.types
    expect(
        unitElement.functionTypeAliases, unorderedEquals([elementA, elementB]));
    // verify delta
    expect(unitDelta.addedDeclarations, unorderedEquals([elementB]));
    expect(unitDelta.removedDeclarations, unorderedEquals([]));
  }

  test_unitMembers_topLevelVariable() {
    _buildOldUnit(r'''
bool a = 1, b = 2;
int c = 3;
''');
    List<CompilationUnitMember> oldNodes = oldUnit.declarations.toList();
    _buildNewUnit(r'''
int c = 3;

bool a =1, b = 2;
''');
    List<CompilationUnitMember> newNodes = newUnit.declarations;
    {
      TopLevelVariableDeclaration newNode = newNodes[0];
      expect(newNode, same(oldNodes[1]));
      expect(getNodeText(newNode), 'int c = 3;');
      {
        TopLevelVariableElement element =
            newNode.variables.variables[0].element;
        expect(element, isNotNull);
        expect(element.name, 'c');
        expect(element.nameOffset, newCode.indexOf('c = 3'));
      }
    }
    {
      TopLevelVariableDeclaration newNode = newNodes[1];
      expect(newNode, same(oldNodes[0]));
      expect(getNodeText(newNode), 'bool a =1, b = 2;');
      {
        TopLevelVariableElement element =
            newNode.variables.variables[0].element;
        expect(element, isNotNull);
        expect(element.name, 'a');
        expect(element.nameOffset, newCode.indexOf('a =1'));
      }
      {
        TopLevelVariableElement element =
            newNode.variables.variables[1].element;
        expect(element, isNotNull);
        expect(element.name, 'b');
        expect(element.nameOffset, newCode.indexOf('b = 2'));
      }
    }
    // verify delta
    expect(unitDelta.addedDeclarations, unorderedEquals([]));
    expect(unitDelta.removedDeclarations, unorderedEquals([]));
  }

  test_unitMembers_topLevelVariable_add() {
    _buildOldUnit(r'''
int a, b;
''');
    List<CompilationUnitMember> oldNodes = oldUnit.declarations.toList();
    _buildNewUnit(r'''
int a, b;
int c, d;
''');
    List<CompilationUnitMember> newNodes = newUnit.declarations;
    // nodes
    TopLevelVariableDeclaration node1 = newNodes[0];
    TopLevelVariableDeclaration node2 = newNodes[1];
    expect(node1, same(oldNodes[0]));
    // elements
    TopLevelVariableElement elementA = node1.variables.variables[0].element;
    TopLevelVariableElement elementB = node1.variables.variables[1].element;
    TopLevelVariableElement elementC = node2.variables.variables[0].element;
    TopLevelVariableElement elementD = node2.variables.variables[1].element;
    expect(elementA, isNotNull);
    expect(elementB, isNotNull);
    expect(elementC, isNotNull);
    expect(elementD, isNotNull);
    expect(elementA.name, 'a');
    expect(elementB.name, 'b');
    expect(elementC.name, 'c');
    expect(elementD.name, 'd');
    // unit.types
    expect(unitElement.topLevelVariables,
        unorderedEquals([elementA, elementB, elementC, elementD]));
    expect(
        unitElement.accessors,
        unorderedEquals([
          elementA.getter,
          elementA.setter,
          elementB.getter,
          elementB.setter,
          elementC.getter,
          elementC.setter,
          elementD.getter,
          elementD.setter
        ]));
  }

  test_unitMembers_topLevelVariable_final() {
    _buildOldUnit(r'''
final int a = 1;
''');
    List<CompilationUnitMember> oldNodes = oldUnit.declarations.toList();
    _buildNewUnit(r'''
final int a =  1;
''');
    List<CompilationUnitMember> newNodes = newUnit.declarations;
    {
      TopLevelVariableDeclaration newNode = newNodes[0];
      expect(newNode, same(oldNodes[0]));
      expect(getNodeText(newNode), 'final int a =  1;');
      {
        TopLevelVariableElement element =
            newNode.variables.variables[0].element;
        expect(element, isNotNull);
        expect(element.name, 'a');
        expect(element.nameOffset, newCode.indexOf('a =  1'));
      }
    }
    // verify delta
    expect(unitDelta.addedDeclarations, unorderedEquals([]));
    expect(unitDelta.removedDeclarations, unorderedEquals([]));
  }

  test_update_addIdentifier_beforeConstructorWithComment() {
    _buildOldUnit(r'''
class A {
  /// CCC
  A();
}
''');
    _buildNewUnit(r'''
class A {
  b

  /// CCC
  A();
}
''');
  }

  test_update_annotation_add() {
    _buildOldUnit(r'''
const myAnnotation = const Object();
foo() {}
''');
    _buildNewUnit(r'''
const myAnnotation = const Object();
@myAnnotation
foo() {}
''');
  }

  test_update_beforeClassWithDelta_nameOffset() {
    _buildOldUnit(r'''
class A {}

class B {
  A a;
}
''');
    _buildNewUnit(r'''
class A2 {}

class B {
  A2 a;
}
''');
  }

  test_update_changeDuplicatingOffsetsMapping() {
    _buildOldUnit(r'''
class A {
  m() {
  }
}

/// X
class C {}
''');
    _buildNewUnit(r'''
class A {
  m2() {
    b
  }
}

/// X
class C {}
''');
  }

  test_update_closuresOfSyntheticInitializer() {
    _buildOldUnit(r'''
f1() {
  print(1);
}
f2() {
  B b = new B((C c) {});
}
''');
    _buildNewUnit(r'''
f1() {
  print(12);
}
f2() {
  B b = new B((C c) {});
}
''');
  }

  test_update_commentReference_empty() {
    _buildOldUnit(r'''
/// Empty [] reference.
class A {}
''');
    _buildNewUnit(r'''
/// Empty [] reference.
class A {}
''');
  }

  test_update_commentReference_multipleCommentTokens() {
    _buildOldUnit(r'''
class A {
  /// C1 [C2]
  /// C3 [C4]
  /// C5 [C6]
  void m() {}
}
''');
    _buildNewUnit(r'''
class A {
  int field;

  /// C1 [C2]
  /// C3 [C4]
  /// C5 [C6]
  void m() {}
}
''');
  }

  test_update_commentReference_new() {
    _buildOldUnit(r'''
/// Comment reference with new [new A].
class A {}
''');
    _buildNewUnit(r'''
class B {}
/// Comment reference with new [new A].
class A {}
''');
  }

  test_update_commentReference_notClosed() {
    _buildOldUnit(r'''
/// [c)
class A {}
''');
    _buildNewUnit(r'''
int a;
/// [c)
class A {}
''');
  }

  test_update_element_implicitAccessors_classField() {
    _buildOldUnit(r'''
// 0
class A {
  var F = 0;
}
''');
    _materializeLazyElements(unitElement);
    _buildNewUnit(r'''
// 012
class A {
  var F = 0;
}
''');
  }

  test_update_element_implicitAccessors_topLevelVariable() {
    _buildOldUnit(r'''
var A = 0;
var B = 1;
''');
    _materializeLazyElements(unitElement);
    _buildNewUnit(r'''
var B = 1;
''');
  }

  test_update_rewrittenConstructorName() {
    _buildOldUnit(r'''
class A {
  A();
  A.named();
}

foo() {}

main() {
  new A();
  new A.named();
}
''');
    _buildNewUnit(r'''
class A {
  A();
  A.named();
}

bar() {}

main() {
  new A();
  new A.named();
}
''');
  }

  void _buildNewUnit(String newCode) {
    this.newCode = newCode;
    AnalysisOptionsImpl analysisOptions = context.analysisOptions;
    analysisOptions.finerGrainedInvalidation = false;
    try {
      context.setContents(source, newCode);
      newUnit = context.parseCompilationUnit(source);
      IncrementalCompilationUnitElementBuilder builder =
          new IncrementalCompilationUnitElementBuilder(oldUnit, newUnit);
      builder.build();
      unitDelta = builder.unitDelta;
      expect(newUnit.element, unitElement);
      // Flush all tokens, ASTs and elements.
      context.analysisCache.flush((target, result) {
        return result == TOKEN_STREAM ||
            result == PARSED_UNIT ||
            RESOLVED_UNIT_RESULTS.contains(result) ||
            LIBRARY_ELEMENT_RESULTS.contains(result);
      });
      // Compute a new AST with built elements.
      CompilationUnit newUnitFull = context.computeResult(
          new LibrarySpecificUnit(source, source), RESOLVED_UNIT1);
      expect(newUnitFull, isNot(same(newUnit)));
      new _BuiltElementsValidator().isEqualNodes(newUnitFull, newUnit);
    } finally {
      analysisOptions.finerGrainedInvalidation = true;
    }
  }

  void _buildOldUnit(String oldCode, [Source libSource]) {
    this.oldCode = oldCode;
    source = newSource('/test.dart', oldCode);
    if (libSource == null) {
      libSource = source;
    }
    oldUnit = context.resolveCompilationUnit2(source, libSource);
    unitElement = oldUnit.element;
    expect(unitElement, isNotNull);
  }

  void _materializeLazyElements(CompilationUnitElement unitElement) {
    unitElement.accept(new _MaterializeLazyElementsVisitor());
  }

  void _verifyNoClassDeltaForTheLast(String oldCode, String newCode) {
    _buildOldUnit(oldCode);
    List<CompilationUnitMember> oldMembers = oldUnit.declarations.toList();
    Element oldElementLast = oldMembers.last.element;
    _buildNewUnit(newCode);
    List<CompilationUnitMember> newMembers = newUnit.declarations;
    Element newElementLast = newMembers.last.element;
    expect(newElementLast, isNot(same(oldElementLast)));
    expect(unitDelta.classDeltas, isEmpty);
    expect(unitDelta.removedDeclarations, unorderedEquals([oldElementLast]));
    expect(unitDelta.addedDeclarations, unorderedEquals([newElementLast]));
  }
}

/**
 * Compares tokens and ASTs, and built elements of declared identifiers.
 */
class _BuiltElementsValidator extends AstComparator {
  final Set visited = new Set.identity();

  @override
  bool isEqualNodes(AstNode expected, AstNode actual) {
    // Elements of nodes which are children of ClassDeclaration(s) must be
    // linked to the corresponding ClassElement(s).
    if (actual is TypeParameter) {
      TypeParameterElement element = actual.element;
      ClassDeclaration classNode = actual.parent.parent;
      expect(element.enclosingElement, same(classNode.element));
    } else if (actual is FieldDeclaration) {
      for (VariableDeclaration field in actual.fields.variables) {
        Element element = field.element;
        ClassDeclaration classNode = actual.parent;
        expect(element.enclosingElement, same(classNode.element));
      }
    } else if (actual is ClassMember) {
      Element element = actual.element;
      ClassDeclaration classNode = actual.parent;
      expect(element.enclosingElement, same(classNode.element));
    }
    // Field elements referenced by field formal parameters of constructors
    // must by fields of the enclosing class element.
    if (actual is FieldFormalParameter) {
      FieldFormalParameterElement parameterElement = actual.element;
      FieldElement element = parameterElement.field;
      ClassDeclaration classNode =
          actual.getAncestor((n) => n is ClassDeclaration);
      expect(element.enclosingElement, same(classNode.element));
    }
    // ElementAnnotationImpl must use the enclosing CompilationUnitElement.
    if (actual is Annotation) {
      AstNode parent = actual.parent;
      if (parent is Declaration) {
        ElementAnnotationImpl actualElement = actual.elementAnnotation;
        CompilationUnitElement enclosingUnitElement =
            parent.element.getAncestor((a) => a is CompilationUnitElement);
        expect(actualElement.compilationUnit, same(enclosingUnitElement));
      }
    }
    // Identifiers like 'a.b' in 'new a.b()' might be rewritten if resolver
    // sees that 'a' is actually a class name, so 'b' is a constructor name.
    //
    if (expected is ConstructorName && actual is ConstructorName) {
      Identifier expectedTypeName = expected.type.name;
      Identifier actualTypeName = actual.type.name;
      if (expectedTypeName is PrefixedIdentifier &&
          actualTypeName is SimpleIdentifier) {
        return isEqualNodes(expectedTypeName.prefix, actualTypeName) &&
            isEqualNodes(expectedTypeName.identifier, actual.name);
      }
    }
    // Compare nodes.
    bool result = super.isEqualNodes(expected, actual);
    if (!result) {
      fail('|$actual| != expected |$expected|');
    }
    // Verify that declared identifiers have equal elements.
    if (expected is SimpleIdentifier && actual is SimpleIdentifier) {
      if (expected.inDeclarationContext()) {
        expect(actual.inDeclarationContext(), isTrue);
        Element expectedElement = expected.staticElement;
        Element actualElement = actual.staticElement;
        _verifyElement(
            expectedElement, actualElement, 'staticElement ($expectedElement)');
      }
    }
    return true;
  }

  void _verifyElement(Element expected, Element actual, String desc) {
    if (!visited.add(expected)) {
      return;
    }
    if (expected == null && actual == null) {
      return;
    }
    // Prefixes are built later.
    if (actual is PrefixElement) {
      return;
    }
    // Compare properties.
    _verifyEqual('$desc name', expected.name, actual.name);
    _verifyEqual('$desc nameOffset', expected.nameOffset, actual.nameOffset);
    if (expected is ElementImpl && actual is ElementImpl) {
      _verifyEqual('$desc codeOffset', expected.codeOffset, actual.codeOffset);
      _verifyEqual('$desc codeLength', expected.codeLength, actual.codeLength);
    }
    if (expected is LocalElement && actual is LocalElement) {
      _verifyEqual(
          '$desc visibleRange', expected.visibleRange, actual.visibleRange);
    }
    _verifyEqual('$desc documentationComment', expected.documentationComment,
        actual.documentationComment);
    {
      var expectedEnclosing = expected.enclosingElement;
      var actualEnclosing = actual.enclosingElement;
      if (expectedEnclosing != null) {
        expect(actualEnclosing, isNotNull, reason: '$desc enclosingElement');
        _verifyElement(expectedEnclosing, actualEnclosing,
            '${expectedEnclosing.name}.$desc');
      }
    }
    // Compare implicit accessors.
    if (expected is PropertyInducingElement &&
        actual is PropertyInducingElement &&
        !expected.isSynthetic) {
      _verifyElement(expected.getter, actual.getter, '$desc getter');
      _verifyElement(expected.setter, actual.setter, '$desc setter');
    }
    // Compare parameters.
    if (expected is ExecutableElement && actual is ExecutableElement) {
      List<ParameterElement> actualParameters = actual.parameters;
      List<ParameterElement> expectedParameters = expected.parameters;
      expect(actualParameters, hasLength(expectedParameters.length));
      for (int i = 0; i < expectedParameters.length; i++) {
        _verifyElement(
            expectedParameters[i], actualParameters[i], '$desc parameters[$i]');
      }
    }
  }

  void _verifyEqual(String name, expected, actual) {
    if (actual != expected) {
      fail('$name\nExpected: $expected\n  Actual: $actual');
    }
  }
}

class _ClassDeltaHelper {
  final String name;

  ClassElementDelta delta;
  ClassElementImpl element;
  int oldVersion;
  List<ClassMember> oldMembers;
  List<ClassMember> newMembers;

  _ClassDeltaHelper(this.name);

  void initNew(CompilationUnit newUnit, CompilationUnitElementDelta unitDelta) {
    expect(element.version, isNot(oldVersion));
    ClassDeclaration newClass = _findClassNode(newUnit, name);
    expect(newClass, isNotNull);
    newMembers = newClass.members.toList();
    delta = unitDelta.classDeltas[name];
    expect(delta, isNotNull, reason: 'No delta for class: $name');
  }

  void initOld(CompilationUnit oldUnit) {
    ClassDeclaration oldClass = _findClassNode(oldUnit, name);
    expect(oldClass, isNotNull);
    element = oldClass.element;
    oldVersion = element.version;
    oldMembers = oldClass.members.toList();
  }

  ClassDeclaration _findClassNode(CompilationUnit unit, String name) =>
      unit.declarations.singleWhere((unitMember) =>
          unitMember is ClassDeclaration && unitMember.name.name == name);
}

class _MaterializeLazyElementsVisitor extends GeneralizingElementVisitor {
  @override
  visitExecutableElement(ExecutableElement element) {
    element.parameters;
    super.visitExecutableElement(element);
  }
}
