/**
  * Index a SQL query result.
  *
  * @param string $type Object type for the index
  * @param string $sql SQL query
  * @param function|array $callback
  */
 protected function sql($type, $sql, $mapping = false, $callback = false)
 {
     $statement = db_query($sql);
     // get type object from index
     $type = $this->index->getType($type);
     if ($mapping) {
         $type->setMapping($mapping);
     }
     // fetch as associative array
     $result = $statement->fetchAll(\PDO::FETCH_ASSOC);
     $i = 0;
     $total = count($result);
     foreach ($result as $data) {
         $data = self::convert($data);
         // array or function callback
         if (is_array($callback)) {
             foreach ($callback as $key => $sql) {
                 $data[$key] = array();
                 // fetch a single column for additional data
                 $result = db_query($sql, array('id' => $data['id']));
                 $result->setFetchMode(\PDO::FETCH_ASSOC);
                 foreach ($result as $object) {
                     $object = self::convert($object);
                     $data[$key][] = $object[$key];
                 }
             }
         } else {
             if ($callback) {
                 $data = $callback($data);
             }
         }
         $this->index($type, $data['id'], $data, isset($data['parent']) ? $data['parent'] : false);
         echo "  Indexing {$type->getName()}... " . ceil(++$i / $total * 100) . "%\r";
     }
     echo "\n";
 }
 /**
  * @return \Elastica_Type
  */
 public function getType()
 {
     return $this->index->getType($this->type);
 }