Commit 904654dc authored by Jens Segers's avatar Jens Segers

More features

parent 9d26ccb9
...@@ -41,7 +41,7 @@ class ConnectionResolver implements ConnectionResolverInterface { ...@@ -41,7 +41,7 @@ class ConnectionResolver implements ConnectionResolverInterface {
* Get a database connection instance. * Get a database connection instance.
* *
* @param string $name * @param string $name
* @return \Illuminate\Database\Connection * @return Connection
*/ */
public function connection($name = null) public function connection($name = null)
{ {
......
...@@ -2,15 +2,9 @@ ...@@ -2,15 +2,9 @@
use Illuminate\Database\ConnectionResolverInterface as Resolver; use Illuminate\Database\ConnectionResolverInterface as Resolver;
use Illuminate\Database\Eloquent\Collection; use Illuminate\Database\Eloquent\Collection;
use Jenssegers\Mongodb\Query as QueryBuilder;
abstract class Model extends \ArrayObject { abstract class Model extends \Illuminate\Database\Eloquent\Model {
/**
* The connection name for the model.
*
* @var string
*/
protected $connection;
/** /**
* The collection associated with the model. * The collection associated with the model.
...@@ -27,225 +21,48 @@ abstract class Model extends \ArrayObject { ...@@ -27,225 +21,48 @@ abstract class Model extends \ArrayObject {
protected $primaryKey = '_id'; protected $primaryKey = '_id';
/** /**
* The connection resolver instance. * Perform a model insert operation.
*
* @var Jenssegers\Mongodb\ConnectionResolverInterface
*/
protected static $resolver;
/**
* Get properties from internal array
*
* @param string $name
* @return mixed
*/
public function __get($name)
{
return $this[$name];
}
/**
* Write all properties to internal array
*
* @param string $name
* @param mixed $value
*/
public function __set($name, $value)
{
$this[$name] = $value;
}
/**
* Handle dynamic method calls into the method.
*
* @param string $method
* @param array $parameters
* @return mixed
*/
public function __call($method, $parameters)
{
// Create a query
$query = $this->newQuery();
return call_user_func_array(array($query, $method), $parameters);
}
/**
* Handle dynamic static method calls into the method.
*
* @param string $method
* @param array $parameters
* @return mixed
*/
public static function __callStatic($method, $parameters)
{
$instance = new static;
return call_user_func_array(array($instance, $method), $parameters);
}
/**
* Get all of the models from the database.
* *
* @param array $columns * @param \Illuminate\Database\Eloquent\Builder
* @return \Illuminate\Database\Eloquent\Collection * @return bool
*/ */
public static function all($columns = array('*')) protected function performInsert($query)
{ {
$instance = new static; if ($this->fireModelEvent('creating') === false) return false;
return $instance->newQuery()->get($columns); $attributes = $this->attributes;
}
/** // If the model has an incrementing key, we can use the "insertGetId" method on
* Find a model by its primary key. // the query builder, which will give us back the final inserted ID for this
* // table from the database. Not all tables have to be incrementing though.
* @param mixed $id if ($this->incrementing)
* @param array $columns
* @return \Jenssegers\Mongodb\Model|\Illuminate\Database\Eloquent\Collection
*/
public static function find($id, $columns = array('*'))
{
$instance = new static;
if (is_array($id))
{ {
$id = array_map(function($value) $keyName = $this->getKeyName();
{ $this->setAttribute($keyName, $query->insert($attributes));
return ($value instanceof MongoID) ? $value : new MongoID($value);
}, $id);
return $instance->newQuery()->whereIn($instance->getKeyName(), $id)->get($columns);
} }
return $instance->newQuery()->find($id, $columns); // If the table is not incrementing we'll simply insert this attributes as they
} // are, as this attributes arrays must contain an "id" column already placed
// there by the developer as the manually determined key for these models.
/** else
* Create a new instance of the given model. {
* $query->insert($attributes);
* @param array $attributes }
* @param bool $exists
* @return \Jenssegers\Mongodb\Model
*/
public function newInstance($attributes = array(), $exists = false)
{
// This method just provides a convenient way for us to generate fresh model
// instances of this current model. It is particularly useful during the
// hydration of new objects via the Eloquent query builder instances.
$model = new static((array) $attributes);
$model->exists = $exists;
return $model;
}
/**
* Get a new query for the model's table.
*
* @return \Jenssegers\Mongodb\Query
*/
public function newQuery()
{
$query = new Query($this);
return $query;
}
/**
* Create a new Collection instance.
*
* @param array $models
* @return LMongo\Eloquent\Collection
*/
public function newCollection(array $models = array())
{
return new Collection($models);
}
/**
* Get the database collection for the model.
*
* @return \Jenssegers\Mongodb\Connection
*/
public function getCollection()
{
return $this->collection;
}
/**
* Get the database connection for the model.
*
* @return \Jenssegers\Mongodb\Connection
*/
public function getConnection()
{
return static::resolveConnection($this->connection);
}
/**
* Get the current connection name for the model.
*
* @return string
*/
public function getConnectionName()
{
return $this->connection;
}
/**
* Set the connection associated with the model.
*
* @param string $name
* @return void
*/
public function setConnection($name)
{
$this->connection = $name;
}
/**
* Get the primary key for the model.
*
* @return string
*/
public function getKeyName()
{
return $this->primaryKey;
}
/** $this->fireModelEvent('created', false);
* Resolve a connection instance by name.
*
* @param string $connection
* @return \Jenssegers\Mongodb\Connection
*/
public static function resolveConnection($connection)
{
return static::$resolver->connection($connection);
}
/** return true;
* Get the connection resolver instance.
*
* @return \Jenssegers\Mongodb\ConnectionResolverInterface
*/
public static function getConnectionResolver()
{
return static::$resolver;
} }
/** /**
* Set the connection resolver instance. * Get a new query builder instance for the connection.
* *
* @param Jenssegers\Mongodb\ConnectionResolverInterface $resolver * @return Builder
* @return void
*/ */
public static function setConnectionResolver(Resolver $resolver) protected function newBaseQueryBuilder()
{ {
static::$resolver = $resolver; $connection = $this->getConnection();
return new QueryBuilder($connection, $this->collection);
} }
} }
\ No newline at end of file
...@@ -2,129 +2,40 @@ ...@@ -2,129 +2,40 @@
use MongoID; use MongoID;
class Query { class Query extends \Illuminate\Database\Query\Builder {
/** /**
* The model. * The database collection
* *
* @var Jenssegers\Mongodb\Model * @var string
*/ */
protected $model; public $collection;
/** /**
* The database connection instance. * All of the available operators.
* *
* @var Jenssegers\Mongodb\Connection * @var array
*/ */
protected $connection;
/**
* The database collection used for the current query.
*
* @var string $collection
*/
protected $collection;
/**
* The where constraints for the query.
*
* @var array
*/
public $wheres = array();
/**
* The columns that should be returned.
*
* @var array
*/
public $columns = array();
/**
* The orderings for the query.
*
* @var array
*/
public $orders = array();
/**
* The maximum number of documents to return.
*
* @var int
*/
public $limit;
/**
* The number of records to skip.
*
* @var int
*/
public $offset;
/**
* All of the available operators.
*
* @var array
*/
protected $operators = array( protected $operators = array(
'=' => '=', '=' => '=',
'!=' => '!=', '!=' => '!=',
'<' => '$lt', '<' => '$lt',
'<=' => '$le', '<=' => '$le',
'>' => '$gt', '>' => '$gt',
'>=' => '$ge' '>=' => '$ge',
'in' => '$in',
); );
/** /**
* Create a new model query builder instance. * Create a new query builder instance.
* *
* @param Jenssegers\Mongodb\Connection $connection * @param Connection $connection
* @return void * @return void
*/ */
public function __construct(Model $model) public function __construct(Connection $connection, $collection)
{
$this->model = $model;
$this->connection = $model->getConnection();
$this->collection = $this->connection->getCollection($model->getCollection());
}
/**
* Set the "limit" value of the query.
*
* @param int $value
* @return \Jenssegers\Mongodb\Query
*/
public function take($value)
{
$this->limit = $value;
return $this;
}
/**
* Set the "offset" value of the query.
*
* @param int $value
* @return \Illuminate\Database\Query\Builder
*/
public function skip($value)
{ {
$this->offset = $value; $this->connection = $connection;
$this->collection = $connection->getCollection($collection);
return $this;
}
/**
* Add an "order by" clause to the query.
*
* @param string $column
* @param string $direction
* @return \Illuminate\Database\Query\Builder
*/
public function orderBy($column, $direction = 'asc')
{
$this->orders[$column] = ($direction == 'asc' ? 1 : -1);
return $this;
} }
/** /**
...@@ -136,69 +47,30 @@ class Query { ...@@ -136,69 +47,30 @@ class Query {
*/ */
public function find($id, $columns = array('*')) public function find($id, $columns = array('*'))
{ {
$id = new MongoID((string) $id); return $this->where('_id', '=', new MongoID((string) $id))->first($columns);
return $this->where($this->model->getKeyName(), '=', $id)->first($columns);
} }
/** /**
* Execute the query and get the first result. * Execute the query as a "select" statement.
* *
* @param array $columns * @param array $columns
* @return array * @return array
*/ */
public function first($columns = array()) public function get($columns = array('*'))
{ {
return $this->take(1)->get($columns)->first(); // If no columns have been specified for the select statement, we will set them
} // here to either the passed columns, or the standard default of retrieving
// all of the columns on the table using the "wildcard" column character.
/** if (is_null($this->columns))
* Add a basic where clause to the query.
*
* @param string $column
* @param string $operator
* @param mixed $value
* @param string $boolean
* @return \Jenssegers\Mongodb\Query
*/
public function where($column, $operator = null, $value = null, $boolean = 'and')
{
// If the given operator is not found in the list of valid operators we will
// assume that the developer is just short-cutting the '=' operators and
// we will set the operators to '=' and set the values appropriately.
if (!in_array(strtolower($operator), $this->operators, true))
{
list($value, $operator) = array($operator, '=');
}
if ($operator == '=')
{ {
$this->wheres[$column] = $value; $this->columns = $columns;
}
else
{
$this->wheres[$column] = array($this->operators[$operator] => $value);
} }
return $this;
}
/**
* Execute the query as a "select" statement.
*
* @param array $columns
* @return Collection
*/
public function get($columns = array())
{
// Merge with previous columns
$this->columns = array_merge($this->columns, $columns);
// Drop all columns if * is present // Drop all columns if * is present
if (in_array('*', $this->columns)) $this->columns = array(); if (in_array('*', $this->columns)) $this->columns = array();
// Get Mongo cursor // Get Mongo cursor
$cursor = $this->collection->find($this->wheres, $this->columns); $cursor = $this->collection->find($this->compileWheres(), $this->columns);
// Apply order // Apply order
if ($this->orders) if ($this->orders)
...@@ -218,57 +90,50 @@ class Query { ...@@ -218,57 +90,50 @@ class Query {
$cursor->limit($this->limit); $cursor->limit($this->limit);
} }
// Return collection of models return $cursor;
return $this->toCollection($cursor);
} }
/** /**
* Insert a new document into the database. * Add an "order by" clause to the query.
* *
* @param array $data * @param string $column
* @return mixed * @param string $direction
* @return \Illuminate\Database\Query\Builder
*/ */
public function insert($data) public function orderBy($column, $direction = 'asc')
{ {
$result = $this->collection->insert($data); $this->orders[$column] = ($direction == 'asc' ? 1 : -1);
if(1 == (int) $result['ok'])
{
return $data['_id'];
}
return false; return $this;
} }
/** /**
* Save the document. Insert into the database if its not exists. * Insert a new record into the database.
* *
* @param array $data * @param array $values
* @return mixed * @return bool
*/ */
public function save($data) public function insert(array $values)
{ {
$this->collection->save($data); $result = $this->collection->insert($values);
if(isset($data['_id'])) if(1 == (int) $result['ok'])
{ {
return $data['_id']; return $values['_id'];
} }
return false;
} }
/** /**
* Update a document in the database. * Update a record in the database.
* *
* @param array $data * @param array $values
* @return int * @return int
*/ */
public function update(array $data) public function update(array $values)
{ {
$update = array('$set' => $data); $update = array('$set' => $values);
$result = $this->collection->update($this->wheres, $update, array('multiple' => true)); $result = $this->collection->update($this->compileWheres(), $update, array('multiple' => true));
if(1 == (int) $result['ok']) if(1 == (int) $result['ok'])
{ {
...@@ -279,13 +144,15 @@ class Query { ...@@ -279,13 +144,15 @@ class Query {
} }
/** /**
* Delete a document from the database. * Delete a record from the database.
* *
* @param mixed $id
* @return int * @return int
*/ */
public function delete() public function delete($id = null)
{ {
$result = $this->collection->remove($this->wheres); $query = $this->compileWheres($this);
$result = $this->collection->remove($query);
if(1 == (int) $result['ok']) if(1 == (int) $result['ok'])
{ {
...@@ -296,20 +163,62 @@ class Query { ...@@ -296,20 +163,62 @@ class Query {
} }
/** /**
* Transform to model collection. * Compile the where array
* *
* @param array $columns * @return array
* @return Collection */
*/ public function compileWheres()
public function toCollection($results) {
if (!$this->wheres) return array();
$wheres = array();
foreach ($this->wheres as $where)
{
// Delegate
$method = "compileWhere{$where['type']}";
$compiled = $this->{$method}($where);
foreach ($compiled as $key=>$value)
$wheres[$key] = $value;
}
return $wheres;
}
public function compileWhereBasic($where)
{
extract($where);
// Convert id's
if ($column == '_id')
{
$value = ($value instanceof MongoID) ? $value : new MongoID($value);
}
// Convert operators
if (!isset($operator) || $operator == '=')
{
return array($column => $value);
}
else
{
return array($column => array($this->operators[$operator] => $value));
}
}
public function compileWhereIn($where)
{ {
$models = array(); extract($where);
foreach ($results as $result) { // Convert id's
$models[] = $this->model->newInstance($result); if ($column == '_id')
{
foreach ($values as &$value)
$value = ($value instanceof MongoID) ? $value : new MongoID($value);
} }
return $this->model->newCollection($models); return array($column => array($this->operators['in'] => $values));
} }
} }
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment