From 51f314e90726560bf2a8a081625902a4096cb3da Mon Sep 17 00:00:00 2001 From: Slam <3lnc.slam@gmail.com> Date: Fri, 28 Nov 2014 13:10:38 +0200 Subject: [PATCH] Doc fixes, thanks @3Inc Author: Slam <3lnc.slam@gmail.com> Date: Fri Nov 28 13:10:38 2014 +0200 --- docs/guide/connecting.rst | 70 +++++++++++++++++++------------ docs/guide/defining-documents.rst | 24 +++++++---- docs/guide/document-instances.rst | 15 +++---- docs/guide/querying.rst | 45 +++++++++++--------- docs/guide/signals.rst | 10 ++--- docs/index.rst | 2 +- mongoengine/base/fields.py | 5 ++- mongoengine/document.py | 3 +- mongoengine/fields.py | 6 +++ mongoengine/queryset/base.py | 3 +- 10 files changed, 112 insertions(+), 71 deletions(-) diff --git a/docs/guide/connecting.rst b/docs/guide/connecting.rst index 0e61df96..48926499 100644 --- a/docs/guide/connecting.rst +++ b/docs/guide/connecting.rst @@ -23,21 +23,32 @@ arguments should be provided:: connect('project1', username='webapp', password='pwd123') -URI style connections are also supported - just supply the uri as +URI style connections are also supported -- just supply the URI as the :attr:`host` to :func:`~mongoengine.connect`:: connect('project1', host='mongodb://localhost/database_name') -Note that database name from uri has priority over name -in :func:`~mongoengine.connect` +.. note:: Database, username and password from URI string overrides + corresponding parameters in :func:`~mongoengine.connect`: :: + + connect( + name='test', + username='user', + password='12345', + host='mongodb://admin:qwerty@localhost/production' + ) + + will establish connection to ``production`` database using + ``admin`` username and ``qwerty`` password. ReplicaSets =========== -MongoEngine supports :class:`~pymongo.mongo_replica_set_client.MongoReplicaSetClient`. -To use them, please use a URI style connection and provide the `replicaSet` name in the -connection kwargs. +MongoEngine supports +:class:`~pymongo.mongo_replica_set_client.MongoReplicaSetClient`. To use them, +please use an URI style connection and provide the ``replicaSet`` name +in the connection kwargs. Read preferences are supported through the connection or via individual queries by passing the read_preference :: @@ -77,36 +88,38 @@ to point across databases and collections. Below is an example schema, using meta = {"db_alias": "users-books-db"} -Switch Database Context Manager -=============================== - -Sometimes you may want to switch the database to query against for a class -for example, archiving older data into a separate database for performance -reasons. +Context Managers +================ +Sometimes you may want to switch the database or collection to query against +for a class. +For example, archiving older data into a separate database for performance +reasons or writing functions that dynamically choose collections to write +document to. +Switch Database +--------------- The :class:`~mongoengine.context_managers.switch_db` context manager allows you to change the database alias for a given class allowing quick and easy -access to the same User document across databases:: +access the same User document across databases:: - from mongoengine.context_managers import switch_db + from mongoengine.context_managers import switch_db - class User(Document): - name = StringField() + class User(Document): + name = StringField() - meta = {"db_alias": "user-db"} + meta = {"db_alias": "user-db"} - with switch_db(User, 'archive-user-db') as User: - User(name="Ross").save() # Saves the 'archive-user-db' + with switch_db(User, 'archive-user-db') as User: + User(name="Ross").save() # Saves the 'archive-user-db' -.. note:: Make sure any aliases have been registered with - :func:`~mongoengine.register_connection` before using the context manager. -There is also a switch collection context manager as well. The -:class:`~mongoengine.context_managers.switch_collection` context manager allows -you to change the collection for a given class allowing quick and easy -access to the same Group document across collection:: +Switch Collection +----------------- +The :class:`~mongoengine.context_managers.switch_collection` context manager +allows you to change the collection for a given class allowing quick and easy +access the same Group document across collection:: - from mongoengine.context_managers import switch_db + from mongoengine.context_managers import switch_collection class Group(Document): name = StringField() @@ -116,3 +129,8 @@ access to the same Group document across collection:: with switch_collection(Group, 'group2000') as Group: Group(name="hello Group 2000 collection!").save() # Saves in group2000 collection + + +.. note:: Make sure any aliases have been registered with + :func:`~mongoengine.register_connection` or :func:`~mongoengine.connect` + before using the context manager. diff --git a/docs/guide/defining-documents.rst b/docs/guide/defining-documents.rst index 315fcde8..5c45c19a 100644 --- a/docs/guide/defining-documents.rst +++ b/docs/guide/defining-documents.rst @@ -4,7 +4,7 @@ Defining documents In MongoDB, a **document** is roughly equivalent to a **row** in an RDBMS. When working with relational databases, rows are stored in **tables**, which have a strict **schema** that the rows follow. MongoDB stores documents in -**collections** rather than tables - the principal difference is that no schema +**collections** rather than tables --- the principal difference is that no schema is enforced at a database level. Defining a document's schema @@ -171,15 +171,15 @@ arguments can be set on all fields: size = StringField(max_length=3, choices=SIZE) :attr:`help_text` (Default: None) - Optional help text to output with the field - used by form libraries + Optional help text to output with the field -- used by form libraries :attr:`verbose_name` (Default: None) - Optional human-readable name for the field - used by form libraries + Optional human-readable name for the field -- used by form libraries List fields ----------- -MongoDB allows the storage of lists of items. To add a list of items to a +MongoDB allows storing lists of items. To add a list of items to a :class:`~mongoengine.Document`, use the :class:`~mongoengine.fields.ListField` field type. :class:`~mongoengine.fields.ListField` takes another field object as its first argument, which specifies which type elements may be stored within the list:: @@ -471,8 +471,16 @@ Text indexes may be specified by prefixing the field name with a **$**. :: class Page(Document): title = StringField() rating = StringField() + created = DateTimeField() meta = { - 'indexes': ['title', ('title', '-rating')] + 'indexes': [ + 'title', + ('title', '-rating'), + { + 'fields': ['created'], + 'expireAfterSeconds': 3600 + } + ] } If a dictionary is passed then the following options are available: @@ -690,7 +698,7 @@ defined, you may subclass it and add any extra fields or methods you may need. As this is new class is not a direct subclass of :class:`~mongoengine.Document`, it will not be stored in its own collection; it will use the same collection as its superclass uses. This allows for more -convenient and efficient retrieval of related documents - all you need do is +convenient and efficient retrieval of related documents -- all you need do is set :attr:`allow_inheritance` to True in the :attr:`meta` data for a document.:: @@ -709,7 +717,7 @@ document.:: Working with existing data -------------------------- -As MongoEngine no longer defaults to needing :attr:`_cls` you can quickly and +As MongoEngine no longer defaults to needing :attr:`_cls`, you can quickly and easily get working with existing data. Just define the document to match the expected schema in your database :: @@ -732,7 +740,7 @@ Abstract classes If you want to add some extra functionality to a group of Document classes but you don't need or want the overhead of inheritance you can use the -:attr:`abstract` attribute of :attr:`-mongoengine.Document.meta`. +:attr:`abstract` attribute of :attr:`~mongoengine.Document.meta`. This won't turn on :ref:`document-inheritance` but will allow you to keep your code DRY:: diff --git a/docs/guide/document-instances.rst b/docs/guide/document-instances.rst index f9a6610f..0e9fcef6 100644 --- a/docs/guide/document-instances.rst +++ b/docs/guide/document-instances.rst @@ -2,7 +2,7 @@ Documents instances =================== To create a new document object, create an instance of the relevant document -class, providing values for its fields as its constructor keyword arguments. +class, providing values for its fields as constructor keyword arguments. You may provide values for any of the fields on the document:: >>> page = Page(title="Test Page") @@ -32,11 +32,11 @@ already exist, then any changes will be updated atomically. For example:: Changes to documents are tracked and on the whole perform ``set`` operations. - * ``list_field.push(0)`` - *sets* the resulting list - * ``del(list_field)`` - *unsets* whole list + * ``list_field.push(0)`` --- *sets* the resulting list + * ``del(list_field)`` --- *unsets* whole list With lists its preferable to use ``Doc.update(push__list_field=0)`` as - this stops the whole list being updated - stopping any race conditions. + this stops the whole list being updated --- stopping any race conditions. .. seealso:: :ref:`guide-atomic-updates` @@ -74,7 +74,7 @@ Cascading Saves If your document contains :class:`~mongoengine.fields.ReferenceField` or :class:`~mongoengine.fields.GenericReferenceField` objects, then by default the :meth:`~mongoengine.Document.save` method will not save any changes to -those objects. If you want all references to also be saved also, noting each +those objects. If you want all references to be saved also, noting each save is a separate query, then passing :attr:`cascade` as True to the save method will cascade any saves. @@ -113,12 +113,13 @@ you may still use :attr:`id` to access the primary key if you want:: >>> bob.id == bob.email == 'bob@example.com' True -You can also access the document's "primary key" using the :attr:`pk` field; in -is an alias to :attr:`id`:: +You can also access the document's "primary key" using the :attr:`pk` field, +it's an alias to :attr:`id`:: >>> page = Page(title="Another Test Page") >>> page.save() >>> page.id == page.pk + True .. note:: diff --git a/docs/guide/querying.rst b/docs/guide/querying.rst index a3496f54..9d1dfd76 100644 --- a/docs/guide/querying.rst +++ b/docs/guide/querying.rst @@ -42,7 +42,7 @@ syntax:: Query operators =============== -Operators other than equality may also be used in queries; just attach the +Operators other than equality may also be used in queries --- just attach the operator name to a key with a double-underscore:: # Only find users whose age is 18 or less @@ -84,19 +84,20 @@ expressions: Geo queries ----------- -There are a few special operators for performing geographical queries. The following -were added in 0.8 for: :class:`~mongoengine.fields.PointField`, +There are a few special operators for performing geographical queries. +The following were added in MongoEngine 0.8 for +:class:`~mongoengine.fields.PointField`, :class:`~mongoengine.fields.LineStringField` and :class:`~mongoengine.fields.PolygonField`: -* ``geo_within`` -- Check if a geometry is within a polygon. For ease of use - it accepts either a geojson geometry or just the polygon coordinates eg:: +* ``geo_within`` -- check if a geometry is within a polygon. For ease of use + it accepts either a geojson geometry or just the polygon coordinates eg:: loc.objects(point__geo_within=[[[40, 5], [40, 6], [41, 6], [40, 5]]]) loc.objects(point__geo_within={"type": "Polygon", "coordinates": [[[40, 5], [40, 6], [41, 6], [40, 5]]]}) -* ``geo_within_box`` - simplified geo_within searching with a box eg:: +* ``geo_within_box`` -- simplified geo_within searching with a box eg:: loc.objects(point__geo_within_box=[(-125.0, 35.0), (-100.0, 40.0)]) loc.objects(point__geo_within_box=[, ]) @@ -132,23 +133,21 @@ were added in 0.8 for: :class:`~mongoengine.fields.PointField`, loc.objects(poly__geo_intersects={"type": "Polygon", "coordinates": [[[40, 5], [40, 6], [41, 6], [41, 5], [40, 5]]]}) -* ``near`` -- Find all the locations near a given point:: +* ``near`` -- find all the locations near a given point:: loc.objects(point__near=[40, 5]) loc.objects(point__near={"type": "Point", "coordinates": [40, 5]}) - - You can also set the maximum distance in meters as well:: + You can also set the maximum distance in meters as well:: loc.objects(point__near=[40, 5], point__max_distance=1000) - The older 2D indexes are still supported with the :class:`~mongoengine.fields.GeoPointField`: * ``within_distance`` -- provide a list containing a point and a maximum distance (e.g. [(41.342, -87.653), 5]) -* ``within_spherical_distance`` -- Same as above but using the spherical geo model +* ``within_spherical_distance`` -- same as above but using the spherical geo model (e.g. [(41.342, -87.653), 5/earth_radius]) * ``near`` -- order the documents by how close they are to a given point * ``near_sphere`` -- Same as above but using the spherical geo model @@ -198,12 +197,14 @@ However, this doesn't map well to the syntax so you can also use a capital S ins Post.objects(comments__by="joe").update(inc__comments__S__votes=1) - .. note:: Due to Mongo currently the $ operator only applies to the first matched item in the query. +.. note:: + Due to :program:`Mongo`, currently the $ operator only applies to the + first matched item in the query. Raw queries ----------- -It is possible to provide a raw PyMongo query as a query parameter, which will +It is possible to provide a raw :mod:`PyMongo` query as a query parameter, which will be integrated directly into the query. This is done using the ``__raw__`` keyword argument:: @@ -213,12 +214,12 @@ keyword argument:: Limiting and skipping results ============================= -Just as with traditional ORMs, you may limit the number of results returned, or +Just as with traditional ORMs, you may limit the number of results returned or skip a number or results in you query. :meth:`~mongoengine.queryset.QuerySet.limit` and :meth:`~mongoengine.queryset.QuerySet.skip` and methods are available on -:class:`~mongoengine.queryset.QuerySet` objects, but the prefered syntax for -achieving this is using array-slicing syntax:: +:class:`~mongoengine.queryset.QuerySet` objects, but the `array-slicing` syntax +is preferred for achieving this:: # Only the first 5 people users = User.objects[:5] @@ -255,7 +256,7 @@ if more than one document matched the query. These exceptions are merged into your document definitions eg: `MyDoc.DoesNotExist` A variation of this method exists, -:meth:`~mongoengine.queryset.Queryset.get_or_create`, that will create a new +:meth:`~mongoengine.queryset.QuerySet.get_or_create`, that will create a new document with the query arguments if no documents match the query. An additional keyword argument, :attr:`defaults` may be provided, which will be used as default values for the new document, in the case that it should need @@ -266,9 +267,13 @@ to be created:: >>> a.name == b.name and a.age == b.age True +.. warning:: + :meth:`~mongoengine.queryset.QuerySet.get_or_create` method is deprecated + since :mod:`mongoengine` 0.8. + Default Document queries ======================== -By default, the objects :attr:`~mongoengine.Document.objects` attribute on a +By default, the objects :attr:`~Document.objects` attribute on a document returns a :class:`~mongoengine.queryset.QuerySet` that doesn't filter the collection -- it returns all objects. This may be changed by defining a method on a document that modifies a queryset. The method should accept two @@ -311,7 +316,7 @@ Should you want to add custom methods for interacting with or filtering documents, extending the :class:`~mongoengine.queryset.QuerySet` class may be the way to go. To use a custom :class:`~mongoengine.queryset.QuerySet` class on a document, set ``queryset_class`` to the custom class in a -:class:`~mongoengine.Document`\ s ``meta`` dictionary:: +:class:`~mongoengine.Document`'s ``meta`` dictionary:: class AwesomerQuerySet(QuerySet): @@ -498,7 +503,7 @@ Documents may be updated atomically by using the There are several different "modifiers" that you may use with these methods: * ``set`` -- set a particular value -* ``unset`` -- delete a particular value (since MongoDB v1.3+) +* ``unset`` -- delete a particular value (since MongoDB v1.3) * ``inc`` -- increment a value by a given amount * ``dec`` -- decrement a value by a given amount * ``push`` -- append a value to a list diff --git a/docs/guide/signals.rst b/docs/guide/signals.rst index fc93e4ca..797a4869 100644 --- a/docs/guide/signals.rst +++ b/docs/guide/signals.rst @@ -35,25 +35,25 @@ Available signals include: :class:`~mongoengine.EmbeddedDocument` instance has been completed. `pre_save` - Called within :meth:`~mongoengine.document.Document.save` prior to performing + Called within :meth:`~mongoengine.Document.save` prior to performing any actions. `pre_save_post_validation` - Called within :meth:`~mongoengine.document.Document.save` after validation + Called within :meth:`~mongoengine.Document.save` after validation has taken place but before saving. `post_save` - Called within :meth:`~mongoengine.document.Document.save` after all actions + Called within :meth:`~mongoengine.Document.save` after all actions (validation, insert/update, cascades, clearing dirty flags) have completed successfully. Passed the additional boolean keyword argument `created` to indicate if the save was an insert or an update. `pre_delete` - Called within :meth:`~mongoengine.document.Document.delete` prior to + Called within :meth:`~mongoengine.Document.delete` prior to attempting the delete operation. `post_delete` - Called within :meth:`~mongoengine.document.Document.delete` upon successful + Called within :meth:`~mongoengine.Document.delete` upon successful deletion of the record. `pre_bulk_insert` diff --git a/docs/index.rst b/docs/index.rst index 77f965ca..2102df02 100644 --- a/docs/index.rst +++ b/docs/index.rst @@ -14,7 +14,7 @@ MongoDB. To install it, simply run MongoEngine. :doc:`guide/index` - The Full guide to MongoEngine - from modeling documents to storing files, + The Full guide to MongoEngine --- from modeling documents to storing files, from querying for data to firing signals and *everything* between. :doc:`apireference` diff --git a/mongoengine/base/fields.py b/mongoengine/base/fields.py index f86d4175..6fad5d63 100644 --- a/mongoengine/base/fields.py +++ b/mongoengine/base/fields.py @@ -428,6 +428,7 @@ class ObjectIdField(BaseField): class GeoJsonBaseField(BaseField): """A geo json field storing a geojson style object. + .. versionadded:: 0.8 """ @@ -436,8 +437,8 @@ class GeoJsonBaseField(BaseField): def __init__(self, auto_index=True, *args, **kwargs): """ - :param auto_index: Automatically create a "2dsphere" index. Defaults - to `True`. + :param bool auto_index: Automatically create a "2dsphere" index.\ + Defaults to `True`. """ self._name = "%sField" % self._type if not auto_index: diff --git a/mongoengine/document.py b/mongoengine/document.py index 1f1f81ae..eecdb57f 100644 --- a/mongoengine/document.py +++ b/mongoengine/document.py @@ -193,7 +193,7 @@ class Document(BaseDocument): in the database doesn't match the query. .. note:: All unsaved changes that has been made to the document are - rejected if the method returns True. + rejected if the method returns True. :param query: the update will be performed only if the document in the database matches the query @@ -250,6 +250,7 @@ class Document(BaseDocument): :param _refs: A list of processed references used in cascading saves :param save_condition: only perform save if matching record in db satisfies condition(s) (e.g., version number) + .. versionchanged:: 0.5 In existing documents it only saves changed fields using set / unset. Saves are cascaded and any diff --git a/mongoengine/fields.py b/mongoengine/fields.py index 5ddcf561..7af64741 100644 --- a/mongoengine/fields.py +++ b/mongoengine/fields.py @@ -1860,6 +1860,7 @@ class PointField(GeoJsonBaseField): to set the value. Requires mongodb >= 2.4 + .. versionadded:: 0.8 """ _type = "Point" @@ -1879,6 +1880,7 @@ class LineStringField(GeoJsonBaseField): You can either pass a dict with the full information or a list of points. Requires mongodb >= 2.4 + .. versionadded:: 0.8 """ _type = "LineString" @@ -1901,6 +1903,7 @@ class PolygonField(GeoJsonBaseField): holes. Requires mongodb >= 2.4 + .. versionadded:: 0.8 """ _type = "Polygon" @@ -1921,6 +1924,7 @@ class MultiPointField(GeoJsonBaseField): to set the value. Requires mongodb >= 2.6 + .. versionadded:: 0.9 """ _type = "MultiPoint" @@ -1941,6 +1945,7 @@ class MultiLineStringField(GeoJsonBaseField): You can either pass a dict with the full information or a list of points. Requires mongodb >= 2.6 + .. versionadded:: 0.9 """ _type = "MultiLineString" @@ -1968,6 +1973,7 @@ class MultiPolygonField(GeoJsonBaseField): of Polygons. Requires mongodb >= 2.6 + .. versionadded:: 0.9 """ _type = "MultiPolygon" diff --git a/mongoengine/queryset/base.py b/mongoengine/queryset/base.py index 39ffa88f..3932465e 100644 --- a/mongoengine/queryset/base.py +++ b/mongoengine/queryset/base.py @@ -402,6 +402,7 @@ class BaseQuerySet(object): will force an fsync on the primary server. :param _from_doc_delete: True when called from document delete therefore signals will have been triggered so don't loop. + :returns number of deleted documents """ queryset = self.clone() @@ -989,7 +990,7 @@ class BaseQuerySet(object): def aggregate(self, *pipeline, **kwargs): """ Perform a aggregate function based in your queryset params - :param pipeline: list of aggregation commands, + :param pipeline: list of aggregation commands,\ see: http://docs.mongodb.org/manual/core/aggregation-pipeline/ .. versionadded:: 0.9