// This file was procedurally generated from the following sources:
// - src/async-generators/yield-star-sync-next.case
// - src/async-generators/default/async-class-expr-static-method.template
/*---
description: execution order for yield* with sync iterator and next() (Static async generator method as a ClassExpression element)
esid: prod-AsyncGeneratorMethod
features: [Symbol.iterator, async-iteration, Symbol.asyncIterator]
flags: [generated, async]
info: |
    ClassElement :
      static MethodDefinition

    MethodDefinition :
      AsyncGeneratorMethod

    Async Generator Function Definitions

    AsyncGeneratorMethod :
      async [no LineTerminator here] * PropertyName ( UniqueFormalParameters ) { AsyncGeneratorBody }


    YieldExpression: yield * AssignmentExpression

    ...
    2. Let value be ? GetValue(exprRef).
    3. Let generatorKind be ! GetGeneratorKind().
    4. Let iterator be ? GetIterator(value, generatorKind).
    5. Let received be NormalCompletion(undefined).
    6. Repeat
      a. If received.[[Type]] is normal, then
        i. Let innerResult be ? IteratorNext(iterator, received.[[Value]]).
        ii. Let innerResult be ? Invoke(iterator, "next",
            « received.[[Value]] »).
        iii. If generatorKind is async, then set innerResult to
             ? Await(innerResult).
        ...
        v. Let done be ? IteratorComplete(innerResult).
        vi. If done is true, then
           1. Return ? IteratorValue(innerResult).
        vii. Let received be GeneratorYield(innerResult).
      ...

    GetIterator ( obj [ , hint ] )

    ...
    3. If hint is async,
      a. Set method to ? GetMethod(obj, @@asyncIterator).
      b. If method is undefined,
        i. Let syncMethod be ? GetMethod(obj, @@iterator).
        ii. Let syncIterator be ? Call(syncMethod, obj).
        iii. Return ? CreateAsyncFromSyncIterator(syncIterator).
    ...

    %AsyncFromSyncIteratorPrototype%.next ( value )

    ...
    5. Let nextResult be IteratorNext(syncIterator, value).
    ...
    7. Let nextValue be IteratorValue(nextResult).
    ...
    9. Let nextDone be IteratorComplete(nextResult).
    ...
    12. Perform ! Call(valueWrapperCapability.[[Resolve]], undefined,
        « nextValue »).
    ...
    14. Set onFulfilled.[[Done]] to nextDone.
    15. Perform ! PerformPromiseThen(valueWrapperCapability.[[Promise]],
        onFulfilled, undefined, promiseCapability).
    ...

    Async Iterator Value Unwrap Functions

    1. Return ! CreateIterResultObject(value, F.[[Done]]).

---*/
var log = [];
var obj = {
  get [Symbol.iterator]() {
    log.push({
      name: "get [Symbol.iterator]",
      thisValue: this
    });
    return function() {
      log.push({
        name: "call [Symbol.iterator]",
        thisValue: this,
        args: [...arguments]
      });
      var nextCount = 0;
      return {
        name: "syncIterator",
        get next() {
          log.push({
            name: "get next",
            thisValue: this
          });
          return function() {
            log.push({
              name: "call next",
              thisValue: this,
              args: [...arguments]
            });

            nextCount++;
            if (nextCount == 1) {
              return {
                name: "next-result-1",
                get value() {
                  log.push({
                    name: "get next value (1)",
                    thisValue: this
                  });
                  return "next-value-1";
                },
                get done() {
                  log.push({
                    name: "get next done (1)",
                    thisValue: this
                  });
                  return false;
                }
              };
            }

            return {
              name: "next-result-2",
              get value() {
                log.push({
                  name: "get next value (2)",
                  thisValue: this
                });
                return "next-value-2";
              },
              get done() {
                log.push({
                  name: "get next done (2)",
                  thisValue: this
                });
                return true;
              }
            };
          };
        }
      };
    };
  },
  get [Symbol.asyncIterator]() {
    log.push({ name: "get [Symbol.asyncIterator]" });
    return null;
  }
};



var callCount = 0;

var C = class { static async *gen() {
    callCount += 1;
    log.push({ name: "before yield*" });
      var v = yield* obj;
      log.push({
        name: "after yield*",
        value: v
      });
      return "return-value";

}}

var gen = C.gen;

var iter = gen();

assert.sameValue(log.length, 0, "log.length");

iter.next("next-arg-1").then(v => {
  assert.sameValue(log[0].name, "before yield*");

  assert.sameValue(log[1].name, "get [Symbol.asyncIterator]");

  assert.sameValue(log[2].name, "get [Symbol.iterator]");
  assert.sameValue(log[2].thisValue, obj, "get [Symbol.iterator] thisValue");

  assert.sameValue(log[3].name, "call [Symbol.iterator]");
  assert.sameValue(log[3].thisValue, obj, "[Symbol.iterator] thisValue");
  assert.sameValue(log[3].args.length, 0, "[Symbol.iterator] args.length");

  assert.sameValue(log[4].name, "get next");
  assert.sameValue(log[4].thisValue.name, "syncIterator", "get next thisValue");

  assert.sameValue(log[5].name, "call next");
  assert.sameValue(log[5].thisValue.name, "syncIterator", "next thisValue");
  assert.sameValue(log[5].args.length, 1, "next args.length");
  assert.sameValue(log[5].args[0], undefined, "next args[0]");

  assert.sameValue(log[6].name, "get next done (1)");
  assert.sameValue(log[6].thisValue.name, "next-result-1", "get next done thisValue");

  assert.sameValue(log[7].name, "get next value (1)");
  assert.sameValue(log[7].thisValue.name, "next-result-1", "get next value thisValue");

  assert.sameValue(v.value, "next-value-1");
  assert.sameValue(v.done, false);

  assert.sameValue(log.length, 8, "log.length");

  iter.next("next-arg-2").then(v => {
    assert.sameValue(log[8].name, "call next");
    assert.sameValue(log[8].thisValue.name, "syncIterator", "next thisValue");
    assert.sameValue(log[8].args.length, 1, "next args.length");
    assert.sameValue(log[8].args[0], "next-arg-2", "next args[0]");

    assert.sameValue(log[9].name, "get next done (2)");
    assert.sameValue(log[9].thisValue.name, "next-result-2", "get next done thisValue");

    assert.sameValue(log[10].name, "get next value (2)");
    assert.sameValue(log[10].thisValue.name, "next-result-2", "get next value thisValue");

    assert.sameValue(log[11].name, "after yield*");
    assert.sameValue(log[11].value, "next-value-2");

    assert.sameValue(v.value, "return-value");
    assert.sameValue(v.done, true);

    assert.sameValue(log.length, 12, "log.length");
  }).then($DONE, $DONE);
}).catch($DONE);

assert.sameValue(callCount, 1);
