<commit_before>'use strict';

var _ = require('lodash');
var Mixin = require('corazon/mixin');
var Promise = require('bluebird');

/**
 * HasMany mixin for model overrides.
 *
 * This mixin separates some of the logic of {@link HasMany} and is only
 * intended to be mixed into that one class.
 */
module.exports = Mixin.create(/** @lends HasMany# */ {

  /**
   * Override of the model's init method.
   *
   * This allows the relation to create a collection cache when new instances
   * are created (those that are not loaded).
   *
   * During the process of creating the model, it checks to see if it was
   * loaded from the database & if it was not, it is assumed to be a brand new
   * object that could not have any associations. It therefore fills the
   * collection cache with an empty array.
   *
   * It is accessible on an individual model via `init`, and as such is an
   * override of the builtin init method.
   *
   * As with all other relation methods, the naming conventions are set forth
   * in {@link BelongsTo.methods}.
   *
   * @method
   * @protected
   * @param {Model} instance The model instance on which to operate.
   * @param {...Object} [args] The arguments to the method.
   * @see {@link BaseRelation#methods}
   */
  initialize: function(relation) {
    return function() {
      this._super.apply(this, arguments);
      relation.afterInitializing(this);
    };
  },

  /**
   * Override of the the model's `_dependents` method.
   *
   * @return {Array.<Model>}
   * @see {@link RelationSave#_dependents}
   */
  dependents: function(/*relation*/) {
    return function() {
      return this._super();
    };
  },

  /**
   * Override of the the model's `_relaints` that adds any related objects that
   * require updating.
   *
   * The models only need to be saved if they will not be processable by
   * {@link HasMany#postsave}. The `postsave` handles foreign key updates,
   * so reliant models are:
   *
   *   - Newly created objects
   *   - Dirty objects, unless only the foreign key is dirty
   *
   * Searches the collection cache and in-flight objects.
   *
   * The resulting objects will be saved before the `postsave`, potentially
   * requiring `postsave` to do less work.
   *
   * @return {Array.<Model>}
   * @see {@link RelationSave#_reliants}
   */
  reliants: function(relation) {
    return function() {
      var result = this._super().slice();
      var foreignKeyAttr = relation.foreignKeyAttr;
      var data = relation._getInFlightData(this);
      var objects = [];
      objects = objects.concat(relation._getCollectionCache(this) || []);
      objects = objects.concat(data.add);
      objects = objects.concat(_.filter(data.remove, 'persisted'));
      _.forEach(objects, function(related) {
        var dirty = _.without(related.dirtyAttributes, foreignKeyAttr);
        var save = dirty.length || related.newRecord;
        if (save) {
          result.push(related);
        }
      });
      return result;
    };
  },

  /**
   * Override of the the model's `_postsave` method.
   *<commit_msg>Added a note about a concern with saving a has-many.<commit_after>'use strict';

var _ = require('lodash');
var Mixin = require('corazon/mixin');
var Promise = require('bluebird');

/**
 * HasMany mixin for model overrides.
 *
 * This mixin separates some of the logic of {@link HasMany} and is only
 * intended to be mixed into that one class.
 */
module.exports = Mixin.create(/** @lends HasMany# */ {

  /**
   * Override of the model's init method.
   *
   * This allows the relation to create a collection cache when new instances
   * are created (those that are not loaded).
   *
   * During the process of creating the model, it checks to see if it was
   * loaded from the database & if it was not, it is assumed to be a brand new
   * object that could not have any associations. It therefore fills the
   * collection cache with an empty array.
   *
   * It is accessible on an individual model via `init`, and as such is an
   * override of the builtin init method.
   *
   * As with all other relation methods, the naming conventions are set forth
   * in {@link BelongsTo.methods}.
   *
   * @method
   * @protected
   * @param {Model} instance The model instance on which to operate.
   * @param {...Object} [args] The arguments to the method.
   * @see {@link BaseRelation#methods}
   */
  initialize: function(relation) {
    return function() {
      this._super.apply(this, arguments);
      relation.afterInitializing(this);
    };
  },

  /**
   * Override of the the model's `_dependents` method.
   *
   * @return {Array.<Model>}
   * @see {@link RelationSave#_dependents}
   */
  dependents: function(/*relation*/) {
    return function() {
      return this._super();
    };
  },

  /**
   * Override of the the model's `_relaints` that adds any related objects that
   * require updating.
   *
   * The models only need to be saved if they will not be processable by
   * {@link HasMany#postsave}. The `postsave` handles foreign key updates,
   * so reliant models are:
   *
   *   - Newly created objects
   *   - Dirty objects, unless only the foreign key is dirty
   *
   * Searches the collection cache and in-flight objects.
   *
   * The resulting objects will be saved before the `postsave`, potentially
   * requiring `postsave` to do less work.
   *
   * @return {Array.<Model>}
   * @see {@link RelationSave#_reliants}
   */
  reliants: function(relation) {
    return function() {
      var result = this._super().slice();
      var foreignKeyAttr = relation.foreignKeyAttr;
      var data = relation._getInFlightData(this);
      var objects = [];

      // TODO: it may not make sense to be reliant on the objects from the
      // collection cache. that would effectively mean that we're trying to
      // traverse the whole model object graph. that's not really the goal. the
      // goal is to save the updated relations. we should really just be
      // concerned with the foreign keys and getting those updated.

      // for instance, if an article fetched 10 comments, they would now be in
      // the collection cache. if each was updated, should saving the article
      // also save them? possibly, but probably not. the article did not
      // change. if the article added a new comment, it has now changed. the
      // change to the article, one could argue, is that it now has a new
      // comment. saving it should only save the new comment (if dirty). the
      // saving of the other updated comments should be the responsibility of
      // the user.

      objects = objects.concat(relation._getCollectionCache(this) || []);
      objects = objects.concat(data.add);
      objects = objects.concat(_.filter(data.remove, 'persisted'));
      _.forEach(objects, function(related) {
        var dirty = _.without(related.dirtyAttributes, foreignKeyAttr);
        var save = dirty.length || related.newRecord;
        if (save) {
          result.push(related);
        }
      });
      return result;
    };
  },

  /**
   * Override of the the model's `_postsave` method.
   *
{'fraction_non_alphanumeric': 0.10279848122626917, 'fraction_numerical': 0.0002812543945999156, 'mean_word_length': 2.782978723404255, 'pattern_counts': {'":': 0, '<': 7, '<?xml version=': 0, '>': 7, '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': '6120235', 'n_tokens_mistral': 2017, 'n_tokens_neox': 1974, 'n_words': 791}