<?php

/**
 * IsisImporterRelations: provides ISIS import methods for importing data
 * into model entities.
 */
class sfIsisImporterRelations extends sfIsisImporterEntities {
  /**
   * Import one to one data.
   *
   * @param object $model    Model
   * @param array  $field    Field data from ISIS database schema
   * @param string $relation Relation name
   */
  public function addOneToOne(&$model, array $field, $relation)
  {
    foreach (new IsisRowIterator($this, $field) as $row)
    {
      $data = new $relation();

      $this->addMain($data, $field, $row);
      $this->addSubfields($data, $field, $row);
      $data->save();

      $key         = sfInflector::underscore($relation) .'_id';
      $model->$key = $data->id;
    }
  }

  /**
   * Import one to many data.
   *
   * @param  object $model    Model
   * @param  string $relation Relation name
   * @return object           Relation model object
   */  
  public function addOneToMany(&$model, $relation)
  {
    $model_id          = $this->getModelId($model);
    $data              = new $relation();
    $data->{$model_id} = $model->id;
    $data->save();
    return $data;
  }

  /**
   * Add simple entities data into the model.
   *
   * @param object $model Model
   * @param array  $field Field data from ISIS database schema
   */  
  public function addOneToManyMain(&$model, array $field, $entity, $key = 'name')
  {
    foreach (new IsisMainItemIterator($this, $field) as $row => $value)
    {
      $this->log("Entity: $entity; Value: $value", 'debug');
      $data         = $this->addOneToMany($model, $entity);
      $data->{$key} = $value;
      $data->save();
    }    
  }

  /**
   * Import a single many to many data.
   *
   * @param object $model    Model
   * @param mixed  $values   Values to be added
   * @param string $relation Relation name
   */
  public function addManyToMany(&$model, $value, $relation)
  {
    $method = 'add'. $relation;

    // Populate related data.
    if (is_callable(array($this, $method)))
    {
      $data = $this->{$method}($value);
    }
    else
    {
      $data = $this->addEntity($relation, $value);
    }

    // Get model and relation names and id fields.
    $model_id                   = $this->getModelId($model);
    $relation_id                = $this->getRelationId($relation);
    $model_relation             = $this->getModelRelation($model, $relation);

    // Make the relation.
    $model_data                 = new $model_relation();
    $model_data->{$model_id}    = $model->id;
    $model_data->{$relation_id} = $data->id;
    $model_data->save();

    return $model_data;
  }

  /**
   * Import many to many data.
   *
   * @param object $model    Model
   * @param array  $values   Values to be added
   * @param string $relation Relation name
   */
  public function addManyToManyEntities(&$model, array $values, $relation)
  {
    foreach ($values as $value)
    {
      $this->addManyToMany($model, $value, $relation);
    }
  }

  /**
   * Add field values in a many-to-many relation.
   *
   * @param object $model    Model
   * @param array  $field    Field data from ISIS database schema
   * @param string $relation Relation name
   */
  public function addManyToManyMain(&$model, array $field, $relation)
  {
    foreach (new IsisMainItemIterator($this, $field) as $value)
    {
      $this->addManyToManyEntities($model, $this->explodeBrackets($value), $relation);
    }    
  }
}