<commit_before>import test from 'ava';

import {
  prepareActions,
  StateTransitionMixin,
  defineActionMethods,
  defineStateTransitionProperties
} from '../src/statetransition-mixin';

const actions = prepareActions({
  start: {
    stopped: {
      target: 'running',
      during: 'starting',
      rejected: 'failed_special',
      timeout: 200
    }
  },
  stop: {
    running: {
      target: 'stopped',
      during: 'stopping',
      rejected: 'failed',
      timeout: 100
    },
    starting: {
      target: 'stopped',
      during: 'stopping',
      timeout: 0
    }
  },
  swim: {
    diving: {
      target: 'swimming'
    }
  }
});

class BaseClass {}

class StatefullClass extends StateTransitionMixin(
  BaseClass,
  actions,
  'stopped'
) {
  constructor(startTime, shouldReject, shouldThrow) {
    super();
    this.startTime = startTime;
    this.shouldReject = shouldReject;
    this.shouldThrow = shouldThrow;
  }
  _start() {
    if (this.startTime === 0) {
      if (this.shouldReject) return Promise.reject(new Error('always reject'));
      if (this.shouldThrow) throw new Error('always throw');
    }
    return new Promise((f, r) => {
      setTimeout(() => {
        if (this.shouldReject) {
          r(Promise.reject(new Error('always reject')));
        }
        if (this.shouldThrow) throw new Error('always throw');
        else {
          f(this);
        }
      }, this.startTime);
    });
  }

  toString() {
    return 'ES2015 class';
  }

  stateChanged(oldState, newState) {
    this._newState = newState;
  }
}

defineActionMethods(StatefullClass.prototype, actions, true);

test('ES2015 class', t =>
  checks(t, (timeout, fail) => new StatefullClass(timeout, fail)));

test('plain object', t =>
  checks(t, (startTime, shouldReject, shouldThrow) => {
    const o = {
      stateChanged(oldState, newState) {
        this._newState = newState;
      },

      toString() {
        return 'plain object';
      },

      _start() {
        if (startTime === 0) {
          if (shouldReject) return Promise.reject(new Error('always reject'));
          if (shouldThrow) throw new Error('always throw');
        }

        return new Promise((f, r) => {
          setTimeout(() => {
            if (shouldReject) {
              r(Promise.reject(new Error('always reject')));
            }
            if (this.shouldThrow) {
              throw new Error('always throw');
            } else {
              f(this);
            }
          }, startTime);
        });
      }
    };
    defineActionMethods(o, actions, true);
    defineStateTransitionProperties(o, actions, 'stopped');

    return o;
  }));

function checks(t, factory) {
  const o = factory(10, false);

  o.state = 'stopped';
  t.is(o.state, 'stopped');

  // has action methods'
  t.truthy(o.stop);
  t.truthy(o.start);
  t.truthy(o._start);<commit_msg>test: avarization ongoing<commit_after>import test from 'ava';

import {
  prepareActions,
  StateTransitionMixin,
  defineActionMethods,
  defineStateTransitionProperties
} from '../src/statetransition-mixin';

const actions = prepareActions({
  start: {
    stopped: {
      target: 'running',
      during: 'starting',
      rejected: 'failed_special',
      timeout: 200
    }
  },
  stop: {
    running: {
      target: 'stopped',
      during: 'stopping',
      rejected: 'failed',
      timeout: 100
    },
    starting: {
      target: 'stopped',
      during: 'stopping',
      timeout: 0
    }
  },
  swim: {
    diving: {
      target: 'swimming'
    }
  }
});

class BaseClass {}

class StatefullClass extends StateTransitionMixin(
  BaseClass,
  actions,
  'stopped'
) {
  constructor(startTime, shouldReject, shouldThrow) {
    super();
    this.startTime = startTime;
    this.shouldReject = shouldReject;
    this.shouldThrow = shouldThrow;
  }
  _start() {
    if (this.startTime === 0) {
      if (this.shouldReject) return Promise.reject(new Error('always reject'));
      if (this.shouldThrow) throw new Error('always throw');
    }
    return new Promise((f, r) => {
      setTimeout(() => {
        if (this.shouldReject) {
          r(Promise.reject(new Error('always reject')));
        }
        if (this.shouldThrow) throw new Error('always throw');
        else {
          f(this);
        }
      }, this.startTime);
    });
  }

  toString() {
    return 'ES2015 class';
  }

  stateChanged(oldState, newState) {
    this._newState = newState;
  }
}

defineActionMethods(StatefullClass.prototype, actions, true);

test('ES2015 class', t =>
  staticChecks(t, (timeout, fail) => new StatefullClass(timeout, fail)));

test('plain object', t =>
  staticChecks(t, (startTime, shouldReject, shouldThrow) => {
    const o = {
      stateChanged(oldState, newState) {
        this._newState = newState;
      },

      toString() {
        return 'plain object';
      },

      _start() {
        if (startTime === 0) {
          if (shouldReject) return Promise.reject(new Error('always reject'));
          if (shouldThrow) throw new Error('always throw');
        }

        return new Promise((f, r) => {
          setTimeout(() => {
            if (shouldReject) {
              r(Promise.reject(new Error('always reject')));
            }
            if (this.shouldThrow) {
              throw new Error('always throw');
            } else {
              f(this);
            }
          }, startTime);
        });
      }
    };
    defineActionMethods(o, actions, true);
    defineStateTransitionProperties(o, actions, 'stopped');

    return o;
  }));

function staticChecks(t, factory) {
  const o = factory(10, false);

  o.state = 'stopped';
  t.is(o.state, 'stopped');

  // has action methods'
  t.truthy(o.stop);
  t.truthy(o.start);
  t.truthy(o._start);
{'fraction_non_alphanumeric': 0.1407986111111111, 'fraction_numerical': 0.006597222222222222, 'mean_word_length': 2.335842501447597, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 19, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5590884', 'n_tokens_mistral': 1820, 'n_tokens_neox': 1781, 'n_words': 393}