데이터베이스 NoSQL 기본 (mongoDB) - 파이썬으로 mongoDB 제어하기 - pymongo 라이브러리

5. 파이썬으로 mongoDB 제어하기 - pymongo 라이브러리

mongodb with EC2 Connection via using pymongo (코드 실행 실습)

import pymongo

5.1. 연결하기

# connection = pymongo.MongoClient(mongo_server, 27017)
username = 'davelee'
password = 'korea123'
connection = pymongo.MongoClient('mongodb://%s:%s@www.funcoding.xyz' % (username, password))

5.2. test Database 사용하기 (없으면 만들어진다.)

db = connection.test
db = connection["test"]   # 이렇게도 가능하다.
print(db)
Database(MongoClient(host=['www.funcoding.xyz:27017'], document_class=dict, tz_aware=False, connect=True), 'test')
print(dir(db))
['_BaseObject__codec_options', '_BaseObject__read_concern', '_BaseObject__read_preference', '_BaseObject__write_concern', '_Database__client', '_Database__incoming_copying_manipulators', '_Database__incoming_manipulators', '_Database__name', '_Database__outgoing_copying_manipulators', '_Database__outgoing_manipulators', '__call__', '__class__', '__delattr__', '__dict__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattr__', '__getattribute__', '__getitem__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__iter__', '__le__', '__lt__', '__module__', '__ne__', '__new__', '__next__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', '__weakref__', '_apply_incoming_copying_manipulators', '_apply_incoming_manipulators', '_collection_default_options', '_command', '_create_or_update_user', '_default_role', '_fix_incoming', '_fix_outgoing', '_legacy_add_user', '_list_collections', 'add_son_manipulator', 'add_user', 'authenticate', 'client', 'codec_options', 'collection_names', 'command', 'create_collection', 'current_op', 'dereference', 'drop_collection', 'error', 'eval', 'get_collection', 'incoming_copying_manipulators', 'incoming_manipulators', 'last_status', 'logout', 'name', 'next', 'outgoing_copying_manipulators', 'outgoing_manipulators', 'previous_error', 'profiling_info', 'profiling_level', 'read_concern', 'read_preference', 'remove_user', 'reset_error_history', 'set_profiling_level', 'system_js', 'validate_collection', 'write_concern']
print(db.name)
test

5.3. test_collection 이라는 collection 사용하기 (없으면 만들어진다.)

test_collection = db.test_collection
test_collection = db["test_collection"]
test_collection
Out[13]:
Collection(Database(MongoClient(host=['www.funcoding.xyz:27017'], document_class=dict, tz_aware=False, connect=True), 'test'), 'test_collection')

5.4. Document INSERT 하기 ( insert_one() 과 insert_many() )

  • insert_one()
post = {"author": "Mike", "text": "My first blog post!", "tags": ["mongodb", "python", "pymongo"] }
test_collection.insert_one(post)
Out[12]:
<pymongo.results.InsertOneResult at 0x1045b5408>
  • Document INSERT 하면, _id (primary key)를 확인하는 방법
post = {"author": "Dave", "text": "My first blog post!", "tags": ["mongodb", "python", "pymongo"] }
post_id = test_collection.insert_one(post).inserted_id
post_id
Out[15]:
ObjectId('5a0ac8dd81f6402f8ff0569f')
  • insert_many()
    • count() 메서드는 컬렉션 객체와 함께 쓰여서 총 Document 수를 알려줌
test_collection.count()    
Out[16]:
23
result = test_collection.insert_many(
    [
        {'number': i} for i in range(10)
    ]
)
test_collection.count()
Out[18]:
33
  • list와 dictionary 를 활용하여 insert 하기
test_insert_collection = db.test_insert  # collection 만들기가 매우 편합니다.
# 리스트, 객체 삽입 가능
test_insert_collection.insert_one({'title' : '암살', 'castings' : ['이정재', '전지현', '하정우']})
test_insert_collection.insert_one({'title' : '실미도', 'castings' : ['설경구', '안성기'], 
                              'datetime' : {'year' : '2003', 'month' : 3,
                                           'val' : {'a' :{'b' : 1}}}})
Out[20]:
<pymongo.results.InsertOneResult at 0x1045c87c8>
data = list()
data.append({'name' : 'aaron', 'age' : 20})
data.append({'name' : 'bob', 'age' : 30})
data.append({'name' : 'cathy', 'age' : 25})
data.append({'name' : 'david', 'age' : 27})
data.append({'name' : 'erick', 'age' : 28})
data.append({'name' : 'fox', 'age' : 32})
data.append({'name' : 'hmm'})

test_insert_collection.insert_many(data)
Out[21]:
<pymongo.results.InsertManyResult at 0x1045b50c8>
for result in test_insert_collection.find():
    print(result)
{'_id': ObjectId('5a01b540c607715c40efc080'), 'title': '암살', 'castings': ['이정재', '전지현', '하정우']}
{'_id': ObjectId('5a01b540c607715c40efc081'), 'title': '실미도', 'castings': ['설경구', '안성기'], 'datetime': {'year': '2003', 'month': 3, 'val': {'a': {'b': 1}}}}
{'_id': ObjectId('5a01b541c607715c40efc082'), 'name': 'aaron', 'age': 20}
{'_id': ObjectId('5a01b541c607715c40efc083'), 'name': 'bob', 'age': 30}
{'_id': ObjectId('5a01b541c607715c40efc084'), 'name': 'cathy', 'age': 25}
{'_id': ObjectId('5a01b541c607715c40efc085'), 'name': 'david', 'age': 27}
{'_id': ObjectId('5a01b541c607715c40efc086'), 'name': 'erick', 'age': 28}
{'_id': ObjectId('5a01b541c607715c40efc087'), 'name': 'fox', 'age': 32}
{'_id': ObjectId('5a01b541c607715c40efc088'), 'name': 'hmm'}
{'_id': ObjectId('5a09890f81f64002aac0bf0b'), 'title': '암살', 'castings': ['이정재', '전지현', '하정우']}
{'_id': ObjectId('5a09890f81f64002aac0bf0c'), 'title': '실미도', 'castings': ['설경구', '안성기'], 'datetime': {'year': '2003', 'month': 3, 'val': {'a': {'b': 1}}}}
{'_id': ObjectId('5a09893f81f64002aac0bf0d'), 'name': 'aaron', 'age': 20}
{'_id': ObjectId('5a09893f81f64002aac0bf0e'), 'name': 'bob', 'age': 30}
{'_id': ObjectId('5a09893f81f64002aac0bf0f'), 'name': 'cathy', 'age': 25}
{'_id': ObjectId('5a09893f81f64002aac0bf10'), 'name': 'david', 'age': 27}
{'_id': ObjectId('5a09893f81f64002aac0bf11'), 'name': 'erick', 'age': 28}
{'_id': ObjectId('5a09893f81f64002aac0bf12'), 'name': 'fox', 'age': 32}
{'_id': ObjectId('5a09893f81f64002aac0bf13'), 'name': 'hmm'}
{'_id': ObjectId('5a0ac98881f6402f8ff056aa'), 'title': '암살', 'castings': ['이정재', '전지현', '하정우']}
{'_id': ObjectId('5a0ac98881f6402f8ff056ab'), 'title': '실미도', 'castings': ['설경구', '안성기'], 'datetime': {'year': '2003', 'month': 3, 'val': {'a': {'b': 1}}}}
{'_id': ObjectId('5a0ac9b681f6402f8ff056ac'), 'name': 'aaron', 'age': 20}
{'_id': ObjectId('5a0ac9b681f6402f8ff056ad'), 'name': 'bob', 'age': 30}
{'_id': ObjectId('5a0ac9b681f6402f8ff056ae'), 'name': 'cathy', 'age': 25}
{'_id': ObjectId('5a0ac9b681f6402f8ff056af'), 'name': 'david', 'age': 27}
{'_id': ObjectId('5a0ac9b681f6402f8ff056b0'), 'name': 'erick', 'age': 28}
{'_id': ObjectId('5a0ac9b681f6402f8ff056b1'), 'name': 'fox', 'age': 32}
{'_id': ObjectId('5a0ac9b681f6402f8ff056b2'), 'name': 'hmm'}
data = test_insert_collection.find()
data
Out[17]:
<pymongo.cursor.Cursor at 0x11180e390>
data_dict = list()
for dat in data:
    print(type(dat))
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>
<class 'dict'>

5.5. Document 검색 하기(읽기) ( find_one() 과 find() )

  • find_one() 메서드 : 가장 빨리 검색되는 하나 검색하기
test_collection.find_one()
Out[24]:
{'_id': ObjectId('5a01b4ba81f6400b2d7c677a'),
 'author': 'Dave',
 'tags': ['mongodb', 'python', 'pymongo'],
 'text': 'My second blog post!'}
test_collection.find_one( {"author":"Dave"} )
Out[25]:
{'_id': ObjectId('5a01b4ba81f6400b2d7c677a'),
 'author': 'Dave',
 'tags': ['mongodb', 'python', 'pymongo'],
 'text': 'My second blog post!'}
  • find_one( 안에 조건을 넣을 때는 사전 형식으로 해야 합니다. { 키:값 } )
  • find() 메서드 : 검색되는 모든 Document 읽어오기
docs = test_collection.find()
for doc in docs:
    print(doc)
{'_id': ObjectId('5a01b4ba81f6400b2d7c677a'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a01b50ec607715c40efc075'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a01b539c607715c40efc076'), 'number': 0}
{'_id': ObjectId('5a01b539c607715c40efc077'), 'number': 1}
{'_id': ObjectId('5a01b539c607715c40efc078'), 'number': 2}
{'_id': ObjectId('5a01b539c607715c40efc079'), 'number': 3}
{'_id': ObjectId('5a01b539c607715c40efc07a'), 'number': 4}
{'_id': ObjectId('5a01b539c607715c40efc07b'), 'number': 5}
{'_id': ObjectId('5a01b54081f6400b2d7c677b'), 'number': 0}
{'_id': ObjectId('5a01b54081f6400b2d7c677c'), 'number': 1}
{'_id': ObjectId('5a01b54081f6400b2d7c677d'), 'number': 2}
{'_id': ObjectId('5a01b54081f6400b2d7c677e'), 'number': 3}
{'_id': ObjectId('5a01b54081f6400b2d7c677f'), 'number': 4}
{'_id': ObjectId('5a01b54081f6400b2d7c6780'), 'number': 5}
{'_id': ObjectId('5a09885481f64002aac0bf00'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a0988a881f64002aac0bf01'), 'number': 0}
{'_id': ObjectId('5a0988a881f64002aac0bf02'), 'number': 1}
{'_id': ObjectId('5a0988a881f64002aac0bf03'), 'number': 2}
{'_id': ObjectId('5a0988a881f64002aac0bf04'), 'number': 3}
{'_id': ObjectId('5a0988a881f64002aac0bf05'), 'number': 4}
{'_id': ObjectId('5a0988a881f64002aac0bf06'), 'number': 5}
{'_id': ObjectId('5a0ac7b581f6402f8ff0569e'), 'author': 'Mike', 'text': 'My first blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a0ac8dd81f6402f8ff0569f'), 'author': 'Dave', 'text': 'My first blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a0'), 'number': 0}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a1'), 'number': 1}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a2'), 'number': 2}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a3'), 'number': 3}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a4'), 'number': 4}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a5'), 'number': 5}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a6'), 'number': 6}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a7'), 'number': 7}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a8'), 'number': 8}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a9'), 'number': 9}
docs = test_collection.find( {"author":"Dave"} )
for doc in docs:
    print(doc)
{'_id': ObjectId('5a01b4ba81f6400b2d7c677a'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a01b50ec607715c40efc075'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a09885481f64002aac0bf00'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a0ac8dd81f6402f8ff0569f'), 'author': 'Dave', 'text': 'My first blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
  • count() 와 함께 쓰기
test_collection.find({"author": "Mike"}).count()
Out[33]:
1
  • sort() 와 함께 쓰기
for post in test_collection.find({"author":"Mike"}).sort("_id"):
    print(post)
{'_id': ObjectId('5a0ac7b581f6402f8ff0569e'), 'author': 'Mike', 'text': 'My first blog post!', 'tags': ['mongodb', 'python', 'pymongo']}

5.6. Document Update 하기 (update_one() 과 update_many())

  • update_one() : 가장 먼저 검색되는 한 Document만 수정하기
test_collection.find_one( {"author":"Dave"} )
Out[35]:
{'_id': ObjectId('5a01b4ba81f6400b2d7c677a'),
 'author': 'Dave',
 'tags': ['mongodb', 'python', 'pymongo'],
 'text': 'My second blog post!'}
test_collection.update_one(
    { "author" : "Dave" }, 
    { "$set" : 
        { "text" : "My second blog post!" }
    }
)
Out[32]:
<pymongo.results.UpdateResult at 0x104d017c8>
docs = test_collection.find( {"author":"Dave"} )
for doc in docs:
    print(doc)
{'_id': ObjectId('5a01b4ba81f6400b2d7c677a'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a01b50ec607715c40efc075'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a09885481f64002aac0bf00'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a0ac8dd81f6402f8ff0569f'), 'author': 'Dave', 'text': 'My first blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
  • update_many() : 조건에 맞는 모든 Document 수정하기
test_collection.update_many({"author": "Dave"}, {"$set": {"text": "My second blog post!"}})
Out[38]:
<pymongo.results.UpdateResult at 0x1045d6fc8>
docs = test_collection.find( {"author":"Dave"} )
for doc in docs:
    print(doc)
{'_id': ObjectId('5a01b4ba81f6400b2d7c677a'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a01b50ec607715c40efc075'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a09885481f64002aac0bf00'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a0ac8dd81f6402f8ff0569f'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}

5.7. Document 삭제 하기 (delete_one() 과 delete_many())

  • delete_one() 메서드 : 가장 먼저 검색되는 한 Document만 삭제하기
docs = test_collection.find( {"author":"Mike"} )
for doc in docs:
    print(doc)
{'_id': ObjectId('5a0ac7b581f6402f8ff0569e'), 'author': 'Mike', 'text': 'My first blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
test_collection.delete_one( {"author":"Mike"} )
Out[43]:
<pymongo.results.DeleteResult at 0x104627888>
docs = test_collection.find( {"author":"Mike"} )
for doc in docs:
    print(doc)
  • delete_many() 메서드 : 조건에 맞는 모든 Document 삭제하기
test_collection.delete_many( {"author":"Mike"} )
Out[46]:
<pymongo.results.DeleteResult at 0x104627d08>
test_collection.find( {"author":"Mike"} ).count()
Out[47]:
0
from pandas import Series, DataFrame

raw_data = {'col0': [1, 2, 3, 4],
            'col1': [10, 20, 30, 40],
            'col2': [100, 200, 300, 400]}

data = DataFrame(raw_data)
data
Out[10]:
col0 col1 col2
0 1 10 100
1 2 20 200
2 3 30 300
3 4 40 400
data_array = data['col1'].as_matrix()
data_array.size
Out[15]:
4
test_collection.find().count()
Out[48]:
32
for doc in test_collection.find():
    print(doc)
{'_id': ObjectId('5a01b4ba81f6400b2d7c677a'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a01b50ec607715c40efc075'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a01b539c607715c40efc076'), 'number': 0}
{'_id': ObjectId('5a01b539c607715c40efc077'), 'number': 1}
{'_id': ObjectId('5a01b539c607715c40efc078'), 'number': 2}
{'_id': ObjectId('5a01b539c607715c40efc079'), 'number': 3}
{'_id': ObjectId('5a01b539c607715c40efc07a'), 'number': 4}
{'_id': ObjectId('5a01b539c607715c40efc07b'), 'number': 5}
{'_id': ObjectId('5a01b54081f6400b2d7c677b'), 'number': 0}
{'_id': ObjectId('5a01b54081f6400b2d7c677c'), 'number': 1}
{'_id': ObjectId('5a01b54081f6400b2d7c677d'), 'number': 2}
{'_id': ObjectId('5a01b54081f6400b2d7c677e'), 'number': 3}
{'_id': ObjectId('5a01b54081f6400b2d7c677f'), 'number': 4}
{'_id': ObjectId('5a01b54081f6400b2d7c6780'), 'number': 5}
{'_id': ObjectId('5a09885481f64002aac0bf00'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a0988a881f64002aac0bf01'), 'number': 0}
{'_id': ObjectId('5a0988a881f64002aac0bf02'), 'number': 1}
{'_id': ObjectId('5a0988a881f64002aac0bf03'), 'number': 2}
{'_id': ObjectId('5a0988a881f64002aac0bf04'), 'number': 3}
{'_id': ObjectId('5a0988a881f64002aac0bf05'), 'number': 4}
{'_id': ObjectId('5a0988a881f64002aac0bf06'), 'number': 5}
{'_id': ObjectId('5a0ac8dd81f6402f8ff0569f'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a0'), 'number': 0}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a1'), 'number': 1}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a2'), 'number': 2}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a3'), 'number': 3}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a4'), 'number': 4}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a5'), 'number': 5}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a6'), 'number': 6}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a7'), 'number': 7}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a8'), 'number': 8}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a9'), 'number': 9}
실습
number 가 6 이상(>=)인 doc 삭제하기
test_collection.delete_many( {"number": { "$gt": 5 } } )
Out[52]:
<pymongo.results.DeleteResult at 0x1046277c8>
for doc in test_collection.find():
    print(doc)
{'_id': ObjectId('5a01b4ba81f6400b2d7c677a'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a01b50ec607715c40efc075'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a01b539c607715c40efc076'), 'number': 0}
{'_id': ObjectId('5a01b539c607715c40efc077'), 'number': 1}
{'_id': ObjectId('5a01b539c607715c40efc078'), 'number': 2}
{'_id': ObjectId('5a01b539c607715c40efc079'), 'number': 3}
{'_id': ObjectId('5a01b539c607715c40efc07a'), 'number': 4}
{'_id': ObjectId('5a01b539c607715c40efc07b'), 'number': 5}
{'_id': ObjectId('5a01b54081f6400b2d7c677b'), 'number': 0}
{'_id': ObjectId('5a01b54081f6400b2d7c677c'), 'number': 1}
{'_id': ObjectId('5a01b54081f6400b2d7c677d'), 'number': 2}
{'_id': ObjectId('5a01b54081f6400b2d7c677e'), 'number': 3}
{'_id': ObjectId('5a01b54081f6400b2d7c677f'), 'number': 4}
{'_id': ObjectId('5a01b54081f6400b2d7c6780'), 'number': 5}
{'_id': ObjectId('5a09885481f64002aac0bf00'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a0988a881f64002aac0bf01'), 'number': 0}
{'_id': ObjectId('5a0988a881f64002aac0bf02'), 'number': 1}
{'_id': ObjectId('5a0988a881f64002aac0bf03'), 'number': 2}
{'_id': ObjectId('5a0988a881f64002aac0bf04'), 'number': 3}
{'_id': ObjectId('5a0988a881f64002aac0bf05'), 'number': 4}
{'_id': ObjectId('5a0988a881f64002aac0bf06'), 'number': 5}
{'_id': ObjectId('5a0ac8dd81f6402f8ff0569f'), 'author': 'Dave', 'text': 'My second blog post!', 'tags': ['mongodb', 'python', 'pymongo']}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a0'), 'number': 0}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a1'), 'number': 1}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a2'), 'number': 2}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a3'), 'number': 3}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a4'), 'number': 4}
{'_id': ObjectId('5a0ac93a81f6402f8ff056a5'), 'number': 5}