コード例 #1
0
    def test_use_schema_resp(
        self,
        api: SpanAPI,
        resp_dump: DumpOptions,
        data_send: Union[Name, dict],
        data_returned: dict,
        error: Optional[Type[errors_api.APIError]],
        bson: bool,
    ):
        @api.route("/test")
        class TestRoute(SpanRoute):
            @api.use_schema(resp=NameSchema(), resp_dump=resp_dump)
            async def on_get(self, req: Request, resp: Response):
                resp.media = data_send

        with api.requests as client:
            if bson:
                headers = {"accept": "application/bson"}
            else:
                headers = {}

            r = client.get("/test", headers=headers)

            if error is not None:
                validate_error(r, error)
            else:
                validate_response(r)

            if error is None:
                if bson:
                    assert dict(RawBSONDocument(r.content)) == dict(
                        RawBSONDocument(BSON.encode(data_returned))
                    )
                else:
                    assert r.json() == data_returned
コード例 #2
0
    def test_raw_bson_document_embedded(self):
        doc = {'embedded': self.document}
        db = self.client.pymongo_test
        db.test_raw.insert_one(doc)
        result = db.test_raw.find_one()
        self.assertEqual(decode(self.document.raw), result['embedded'])

        # Make sure that CodecOptions are preserved.
        # {'embedded': [
        #   {'date': datetime.datetime(2015, 6, 3, 18, 40, 50, 826000),
        #    '_id': UUID('026fab8f-975f-4965-9fbf-85ad874c60ff')}
        # ]}
        # encoded with JAVA_LEGACY uuid representation.
        bson_string = (
            b'D\x00\x00\x00\x04embedded\x005\x00\x00\x00\x030\x00-\x00\x00\x00'
            b'\tdate\x00\x8a\xd6\xb9\xbaM\x01\x00\x00\x05_id\x00\x10\x00\x00'
            b'\x00\x03eI_\x97\x8f\xabo\x02\xff`L\x87\xad\x85\xbf\x9f\x00\x00'
            b'\x00'
        )
        rbd = RawBSONDocument(
            bson_string,
            codec_options=CodecOptions(uuid_representation=JAVA_LEGACY,
                                       document_class=RawBSONDocument))

        db.test_raw.drop()
        db.test_raw.insert_one(rbd)
        result = db.get_collection('test_raw', codec_options=CodecOptions(
            uuid_representation=JAVA_LEGACY)).find_one()
        self.assertEqual(rbd['embedded'][0]['_id'],
                         result['embedded'][0]['_id'])
コード例 #3
0
    def insert_data_key(self, data_key):
        """Insert a data key into the key vault.

        :Parameters:
          - `data_key`: The data key document to insert.

        :Returns:
          The _id of the inserted data key document.
        """
        raw_doc = RawBSONDocument(data_key)
        data_key_id = raw_doc.get('_id')
        if not isinstance(data_key_id, uuid.UUID):
            raise TypeError('data_key _id must be a UUID')

        self.key_vault_coll.insert_one(raw_doc)
        return Binary(data_key_id.bytes, subtype=UUID_SUBTYPE)
コード例 #4
0
def load_file(file_path: str, session: Session) -> None:
    """Loads the file to the databases.

    If there already is a file with the same pk, then nothing is done.

    The json is converted into BSON and it's stored like this in the database
    to avoid problems with dots in the keys.
    """
    try:
        with open(file_path) as f:
            log.info(f"Loading {file_path}")
            chunk = loads(f.read())

            doc_id = chunk["pk"]
            chunk["_id"] = doc_id
            chunk[FETCHED_FIELD_NAME] = False

            chunk = RawBSONDocument(bson.BSON.encode(chunk))

            if session.collection.count_documents({"_id": doc_id}) != 0:
                log.info(
                    f"Skipping - there is already a document with id={doc_id}")
            else:
                session.collection.insert_one(chunk)
    except Exception as e:
        log.error(f"{e}")
コード例 #5
0
 def raw_response(self, cursor_id=None, user_fields={}):  # noqa: B006
     """
     cursor_id is ignored
     user_fields is used to determine which fields must not be decoded
     """
     inflated_response = _decode_selective(
         RawBSONDocument(self.payload_document), user_fields,
         DEFAULT_RAW_BSON_OPTIONS)
     return [inflated_response]
コード例 #6
0
def bson_decode(
        content: bytes) -> Union[RawBSONDocument, List[RawBSONDocument]]:
    """
    Decodes ``content`` bytes to RawBSONDocument(s)
    """
    if content.startswith(BSON_RECORD_DELIM):
        return bson_decode_list(content)
    else:
        return RawBSONDocument(content)
コード例 #7
0
    def test_preserve_key_ordering(self):
        keyvaluepairs = [
            ('a', 1),
            ('b', 2),
            ('c', 3),
        ]
        rawdoc = RawBSONDocument(encode(SON(keyvaluepairs)))

        for rkey, elt in zip(rawdoc, keyvaluepairs):
            self.assertEqual(rkey, elt[0])
コード例 #8
0
def bson_decode_list(content: bytes) -> List[RawBSONDocument]:
    record_raw_list = content.split(BSON_RECORD_DELIM)
    # The first record is always going to be blank.
    record_raw_list.pop(0)
    loaded_list: List[RawBSONDocument] = list()

    for record_raw in record_raw_list:
        loaded_list.append(RawBSONDocument(record_raw))

    return loaded_list
コード例 #9
0
    def fetch_keys(self, filter):
        """Yields one or more keys from the key vault.

        :Parameters:
          - `filter`: The filter to pass to find.

        :Returns:
          A generator which yields the requested keys from the key vault.
        """
        with self.key_vault_coll.find(RawBSONDocument(filter)) as cursor:
            for key in cursor:
                yield key.raw
コード例 #10
0
    def test_round_trip_raw_uuid(self):
        coll = self.client.get_database('pymongo_test').test_raw
        uid = uuid.uuid4()
        doc = {'_id': 1,
               'bin4': Binary(uid.bytes, 4),
               'bin3': Binary(uid.bytes, 3)}
        raw = RawBSONDocument(encode(doc))
        coll.insert_one(raw)
        self.assertEqual(coll.find_one(), {'_id': 1, 'bin4': uid, 'bin3': uid})

        # Test that the raw bytes haven't changed.
        raw_coll = coll.with_options(codec_options=DEFAULT_RAW_BSON_OPTIONS)
        self.assertEqual(raw_coll.find_one(), raw)
コード例 #11
0
 async def on_get(self, req: Request, resp: Response):
     resp.media = RawBSONDocument(
         BSON.encode(
             {
                 "id": uuid_value,
                 "dt": dt_value,
                 # "binary": bytes_value,
                 "info": info_value,
                 "array": array_value,
                 "empty": {},
             }
         )
     )
コード例 #12
0
 def test_raw(self):
     """Test with RawBSONDocument."""
     raw_coll = self.coll.with_options(
         codec_options=DEFAULT_RAW_BSON_OPTIONS)
     with raw_coll.watch() as change_stream:
         raw_doc = RawBSONDocument(BSON.encode({'_id': 1}))
         self.coll.insert_one(raw_doc)
         change = next(change_stream)
         self.assertIsInstance(change, RawBSONDocument)
         self.assertEqual(change['operationType'], 'insert')
         self.assertEqual(change['ns']['db'], self.coll.database.name)
         self.assertEqual(change['ns']['coll'], self.coll.name)
         self.assertEqual(change['fullDocument'], raw_doc)
         self.assertEqual(change['_id'], change_stream._resume_token)
コード例 #13
0
    def test_with_codec_options(self):
        # {u'date': datetime.datetime(2015, 6, 3, 18, 40, 50, 826000),
        #  u'_id': UUID('026fab8f-975f-4965-9fbf-85ad874c60ff')}
        # encoded with JAVA_LEGACY uuid representation.
        bson_string = (
            b'-\x00\x00\x00\x05_id\x00\x10\x00\x00\x00\x03eI_\x97\x8f\xabo\x02'
            b'\xff`L\x87\xad\x85\xbf\x9f\tdate\x00\x8a\xd6\xb9\xbaM'
            b'\x01\x00\x00\x00')
        document = RawBSONDocument(
            bson_string,
            codec_options=CodecOptions(uuid_representation=JAVA_LEGACY))

        self.assertEqual(uuid.UUID('026fab8f-975f-4965-9fbf-85ad874c60ff'),
                         document['_id'])
コード例 #14
0
 def test_round_trip_codec_options(self):
     doc = {
         'date': datetime.datetime(2015, 6, 3, 18, 40, 50, 826000),
         '_id': uuid.UUID('026fab8f-975f-4965-9fbf-85ad874c60ff')
     }
     db = self.client.pymongo_test
     coll = db.get_collection(
         'test_raw',
         codec_options=CodecOptions(uuid_representation=JAVA_LEGACY))
     coll.insert_one(doc)
     raw_java_legacy = CodecOptions(uuid_representation=JAVA_LEGACY,
                                    document_class=RawBSONDocument)
     coll = db.get_collection('test_raw', codec_options=raw_java_legacy)
     self.assertEqual(
         RawBSONDocument(encode(doc, codec_options=raw_java_legacy)),
         coll.find_one())
コード例 #15
0
    def collection_info(self, database, filter):
        """Get the collection info for a namespace.

        The returned collection info is passed to libmongocrypt which reads
        the JSON schema.

        :Parameters:
          - `database`: The database on which to run listCollections.
          - `filter`: The filter to pass to listCollections.

        :Returns:
          The first document from the listCollections command response as BSON.
        """
        with self.client_ref()[database].list_collections(
                filter=RawBSONDocument(filter)) as cursor:
            for doc in cursor:
                return _dict_to_bson(doc, False, _DATA_KEY_OPTS)
コード例 #16
0
    def test_req_load_schema(
        self,
        api: SpanAPI,
        req_load: LoadOptions,
        data_post: dict,
        data_passed: Union[Name, dict],
        error: Optional[Type[errors_api.APIError]],
        bson: bool,
    ):
        if bson and isinstance(data_passed, dict):
            data_passed = RawBSONDocument(BSON.encode(data_passed))

        @api.route("/test")
        class TestRoute(SpanRoute):
            @api.use_schema(req=NameSchema(), req_load=req_load)
            async def on_post(
                self, req: Request[dict, Union[Name, dict]], resp: Response
            ):
                data = await req.media_loaded()
                if req_load is LoadOptions.IGNORE:
                    assert data == data_passed
                    assert await req.media() == data_passed
                else:
                    assert isinstance(data, type(data_passed))
                    assert data == data_passed

        with api.requests as client:
            if bson:
                if isinstance(data_post, dict):
                    data_post = BSON.encode(data_post)

                r = client.post(
                    "/test",
                    data=data_post,
                    headers={"Content-Type": "application/bson"},
                )
            else:
                r = client.post("/test", json=data_post)

            if error is not None:
                validate_error(r, error)
            else:
                validate_response(r)
コード例 #17
0
    def test_dump_bson_compatible_objects(
        self, mimetype, feed_bson: bool, feed_list: bool
    ):
        data = {
            "uuid": uuid.uuid4(),
            "datetime": dt_factory(),
            "bytes": b"Some Bin Data",
            "raw_bson": RawBSONDocument(
                BSON.encode({"key": "value", "nested": {"key": "value"}})
            ),
            "raw_bson_list": [
                RawBSONDocument(
                    BSON.encode({"key": "value", "nested": {"key": "value"}})
                ),
                RawBSONDocument(
                    BSON.encode({"key": "value", "nested": {"key": "value"}})
                ),
            ],
        }
        if feed_bson:
            data = RawBSONDocument(BSON.encode(data))
        if feed_list:
            data = [data, data]
        headers = dict()

        encoded = encode_content(data, mimetype=mimetype, headers=headers)
        try:
            print("ENCODED:", encoded.decode(), "", sep="\n")
        except BaseException:
            print("ENCODED:", encoded, "", sep="\n")

        loaded, decoded = decode_content(encoded, mimetype=mimetype)

        print("DECODED:", loaded, sep="\n")

        if feed_list:
            loaded = loaded[0]
            data = data[0]
            data = dict(data)
            data["raw_bson"] = dict(data["raw_bson"])
            data["raw_bson"]["nested"] = dict(data["raw_bson"]["nested"])

        assert str(loaded["uuid"]) == str(data["uuid"])
        assert set(loaded.keys()) == set(data.keys())
     # noqa: E501

    :param body: ${KEY} to be created
    :type body: dict | bytes

    :rtype: str
    """
    if connexion.request.is_json:
        body = connexion.request.get_json()  # noqa: E501

    doc_id = str(uuid.uuid4())
    body['_id'] = doc_id
    body['_sys'] = {'created_ts': int(time.time()), 'created_by': connexion.request.headers['x-api-user']}
    body_str = json.dumps(body)
    collection.insert_one(RawBSONDocument(bsonjs.loads(body_str)))

    qKey='{}{}'.format(KEY, dpath(body))
    publisher(body_str, routing_key='{}.create'.format(qKey), retry=True, declare=createQueues(qKey), headers={'_id':doc_id})

    skey = '{}|{}'.format(KEY, doc_id)
    r.set(skey, body_str, ex=3)
    r.delete(KEY)

    return doc_id


def delete${KEY}(ID):  # noqa: E501
    """Delete the ${KEY} instance based on ID

     # noqa: E501
コード例 #19
0
 def insert(self, document):
     self.inserted_items.append(document)
     return InsertOneResult(RawBSONDocument(BSON.encode(document)), True)
コード例 #20
0
 def test_invalid_bson_eoo(self):
     invalid_bson_eoo = encode({'a': 1})[:-1] + b'\x01'
     with self.assertRaisesRegex(InvalidBSON, 'bad eoo'):
         RawBSONDocument(invalid_bson_eoo)
コード例 #21
0
 def test_invalid_bson_sequence(self):
     bson_byte_sequence = encode({'a': 1})+encode({})
     with self.assertRaisesRegex(InvalidBSON, 'invalid object length'):
         RawBSONDocument(bson_byte_sequence)
コード例 #22
0
 def test_empty_doc(self):
     doc = RawBSONDocument(encode({}))
     with self.assertRaises(KeyError):
         doc['does-not-exist']
コード例 #23
0
class TestRawBSONDocument(IntegrationTest):

    # {'_id': ObjectId('556df68b6e32ab21a95e0785'),
    #  'name': 'Sherlock',
    #  'addresses': [{'street': 'Baker Street'}]}
    bson_string = (
        b'Z\x00\x00\x00\x07_id\x00Um\xf6\x8bn2\xab!\xa9^\x07\x85\x02name\x00\t'
        b'\x00\x00\x00Sherlock\x00\x04addresses\x00&\x00\x00\x00\x030\x00\x1e'
        b'\x00\x00\x00\x02street\x00\r\x00\x00\x00Baker Street\x00\x00\x00\x00'
    )
    document = RawBSONDocument(bson_string)

    @classmethod
    def setUpClass(cls):
        super(TestRawBSONDocument, cls).setUpClass()
        client_context.client = rs_or_single_client()
        cls.client = client_context.client

    def tearDown(self):
        if client_context.connected:
            self.client.pymongo_test.test_raw.drop()

    def test_decode(self):
        self.assertEqual('Sherlock', self.document['name'])
        first_address = self.document['addresses'][0]
        self.assertIsInstance(first_address, RawBSONDocument)
        self.assertEqual('Baker Street', first_address['street'])

    def test_raw(self):
        self.assertEqual(self.bson_string, self.document.raw)

    def test_empty_doc(self):
        doc = RawBSONDocument(encode({}))
        with self.assertRaises(KeyError):
            doc['does-not-exist']

    def test_invalid_bson_sequence(self):
        bson_byte_sequence = encode({'a': 1})+encode({})
        with self.assertRaisesRegex(InvalidBSON, 'invalid object length'):
            RawBSONDocument(bson_byte_sequence)

    def test_invalid_bson_eoo(self):
        invalid_bson_eoo = encode({'a': 1})[:-1] + b'\x01'
        with self.assertRaisesRegex(InvalidBSON, 'bad eoo'):
            RawBSONDocument(invalid_bson_eoo)

    @client_context.require_connection
    def test_round_trip(self):
        db = self.client.get_database(
            'pymongo_test',
            codec_options=CodecOptions(document_class=RawBSONDocument))
        db.test_raw.insert_one(self.document)
        result = db.test_raw.find_one(self.document['_id'])
        self.assertIsInstance(result, RawBSONDocument)
        self.assertEqual(dict(self.document.items()), dict(result.items()))

    @client_context.require_connection
    def test_round_trip_raw_uuid(self):
        coll = self.client.get_database('pymongo_test').test_raw
        uid = uuid.uuid4()
        doc = {'_id': 1,
               'bin4': Binary(uid.bytes, 4),
               'bin3': Binary(uid.bytes, 3)}
        raw = RawBSONDocument(encode(doc))
        coll.insert_one(raw)
        self.assertEqual(coll.find_one(), doc)
        uuid_coll = coll.with_options(
            codec_options=coll.codec_options.with_options(
                uuid_representation=UuidRepresentation.STANDARD))
        self.assertEqual(uuid_coll.find_one(),
                         {'_id': 1, 'bin4': uid, 'bin3': Binary(uid.bytes, 3)})

        # Test that the raw bytes haven't changed.
        raw_coll = coll.with_options(codec_options=DEFAULT_RAW_BSON_OPTIONS)
        self.assertEqual(raw_coll.find_one(), raw)

    def test_with_codec_options(self):
        # {'date': datetime.datetime(2015, 6, 3, 18, 40, 50, 826000),
        #  '_id': UUID('026fab8f-975f-4965-9fbf-85ad874c60ff')}
        # encoded with JAVA_LEGACY uuid representation.
        bson_string = (
            b'-\x00\x00\x00\x05_id\x00\x10\x00\x00\x00\x03eI_\x97\x8f\xabo\x02'
            b'\xff`L\x87\xad\x85\xbf\x9f\tdate\x00\x8a\xd6\xb9\xbaM'
            b'\x01\x00\x00\x00'
        )
        document = RawBSONDocument(
            bson_string,
            codec_options=CodecOptions(uuid_representation=JAVA_LEGACY,
                                       document_class=RawBSONDocument))

        self.assertEqual(uuid.UUID('026fab8f-975f-4965-9fbf-85ad874c60ff'),
                         document['_id'])

    @client_context.require_connection
    def test_round_trip_codec_options(self):
        doc = {
            'date': datetime.datetime(2015, 6, 3, 18, 40, 50, 826000),
            '_id': uuid.UUID('026fab8f-975f-4965-9fbf-85ad874c60ff')
        }
        db = self.client.pymongo_test
        coll = db.get_collection(
            'test_raw',
            codec_options=CodecOptions(uuid_representation=JAVA_LEGACY))
        coll.insert_one(doc)
        raw_java_legacy = CodecOptions(uuid_representation=JAVA_LEGACY,
                                       document_class=RawBSONDocument)
        coll = db.get_collection('test_raw', codec_options=raw_java_legacy)
        self.assertEqual(
            RawBSONDocument(encode(doc, codec_options=raw_java_legacy)),
            coll.find_one())

    @client_context.require_connection
    def test_raw_bson_document_embedded(self):
        doc = {'embedded': self.document}
        db = self.client.pymongo_test
        db.test_raw.insert_one(doc)
        result = db.test_raw.find_one()
        self.assertEqual(decode(self.document.raw), result['embedded'])

        # Make sure that CodecOptions are preserved.
        # {'embedded': [
        #   {'date': datetime.datetime(2015, 6, 3, 18, 40, 50, 826000),
        #    '_id': UUID('026fab8f-975f-4965-9fbf-85ad874c60ff')}
        # ]}
        # encoded with JAVA_LEGACY uuid representation.
        bson_string = (
            b'D\x00\x00\x00\x04embedded\x005\x00\x00\x00\x030\x00-\x00\x00\x00'
            b'\tdate\x00\x8a\xd6\xb9\xbaM\x01\x00\x00\x05_id\x00\x10\x00\x00'
            b'\x00\x03eI_\x97\x8f\xabo\x02\xff`L\x87\xad\x85\xbf\x9f\x00\x00'
            b'\x00'
        )
        rbd = RawBSONDocument(
            bson_string,
            codec_options=CodecOptions(uuid_representation=JAVA_LEGACY,
                                       document_class=RawBSONDocument))

        db.test_raw.drop()
        db.test_raw.insert_one(rbd)
        result = db.get_collection('test_raw', codec_options=CodecOptions(
            uuid_representation=JAVA_LEGACY)).find_one()
        self.assertEqual(rbd['embedded'][0]['_id'],
                         result['embedded'][0]['_id'])

    @client_context.require_connection
    def test_write_response_raw_bson(self):
        coll = self.client.get_database(
            'pymongo_test',
            codec_options=CodecOptions(document_class=RawBSONDocument)).test_raw

        # No Exceptions raised while handling write response.
        coll.insert_one(self.document)
        coll.delete_one(self.document)
        coll.insert_many([self.document])
        coll.delete_many(self.document)
        coll.update_one(self.document, {'$set': {'a': 'b'}}, upsert=True)
        coll.update_many(self.document, {'$set': {'b': 'c'}})

    def test_preserve_key_ordering(self):
        keyvaluepairs = [('a', 1), ('b', 2), ('c', 3),]
        rawdoc = RawBSONDocument(encode(SON(keyvaluepairs)))

        for rkey, elt in zip(rawdoc, keyvaluepairs):
            self.assertEqual(rkey, elt[0])
コード例 #24
0
class TestUseSchemaReq:
    @pytest.mark.parametrize(
        "req_load,data_post,data_passed,error",
        [
            # Tests normal loading to dataclass object
            (LoadOptions.VALIDATE_AND_LOAD, HARRY_DUMPED, HARRY, None),
            # Tests validation error on loading bad data
            (
                LoadOptions.VALIDATE_AND_LOAD,
                HARRY_BAD_ID,
                None,
                errors_api.RequestValidationError,
            ),
            # Tests validation error on loading bad data
            (
                LoadOptions.VALIDATE_AND_LOAD,
                DRACO_DUMPED,
                None,
                errors_api.RequestValidationError,
            ),
            # Tests validation error on load for not a json
            (
                LoadOptions.VALIDATE_AND_LOAD,
                "notajson",
                None,
                errors_api.RequestValidationError,
            ),
            # Tests successful validation of incoming data without a load
            (LoadOptions.VALIDATE_ONLY, HARRY_DUMPED, HARRY_DUMPED, None),
            # Tests validation error on validate-only bad data.
            (
                LoadOptions.VALIDATE_ONLY,
                HARRY_BAD_ID,
                None,
                errors_api.RequestValidationError,
            ),
            # Tests validation error on validate-only bad data.
            (
                LoadOptions.VALIDATE_ONLY,
                DRACO_DUMPED,
                None,
                errors_api.RequestValidationError,
            ),
            # Tests validation error on validate for not a json
            (
                LoadOptions.VALIDATE_ONLY,
                "notajson",
                None,
                errors_api.RequestValidationError,
            ),
            # Tests successful ignore of good data
            (LoadOptions.IGNORE, HARRY_DUMPED, HARRY_DUMPED, None),
            # Tests successful ignore of bad data
            (LoadOptions.IGNORE, HARRY_BAD_ID, HARRY_BAD_ID, None),
            # Tests successful ignore of bad data
            (LoadOptions.IGNORE, DRACO_DUMPED, DRACO_DUMPED, None),
        ],
    )
    @pytest.mark.parametrize("bson", [True, False])
    def test_req_load_schema(
        self,
        api: SpanAPI,
        req_load: LoadOptions,
        data_post: dict,
        data_passed: Union[Name, dict],
        error: Optional[Type[errors_api.APIError]],
        bson: bool,
    ):
        if bson and isinstance(data_passed, dict):
            data_passed = RawBSONDocument(BSON.encode(data_passed))

        @api.route("/test")
        class TestRoute(SpanRoute):
            @api.use_schema(req=NameSchema(), req_load=req_load)
            async def on_post(
                self, req: Request[dict, Union[Name, dict]], resp: Response
            ):
                data = await req.media_loaded()
                if req_load is LoadOptions.IGNORE:
                    assert data == data_passed
                    assert await req.media() == data_passed
                else:
                    assert isinstance(data, type(data_passed))
                    assert data == data_passed

        with api.requests as client:
            if bson:
                if isinstance(data_post, dict):
                    data_post = BSON.encode(data_post)

                r = client.post(
                    "/test",
                    data=data_post,
                    headers={"Content-Type": "application/bson"},
                )
            else:
                r = client.post("/test", json=data_post)

            if error is not None:
                validate_error(r, error)
            else:
                validate_response(r)

    def test_req_load_schema_class(self, api: SpanAPI):
        @api.route("/test")
        class TestRoute(SpanRoute):
            @api.use_schema(req=NameSchema)
            async def on_post(self, req: Request, resp: Response):
                assert await req.media_loaded() == HARRY

        with api.requests as client:
            r = client.post("/test", json=HARRY_DUMPED)
            validate_response(r)

    @pytest.mark.parametrize(
        "data",
        [
            [HARRY_DUMPED, HARRY_DUMPED],
            [
                RawBSONDocument(BSON.encode(HARRY_DUMPED)),
                RawBSONDocument(BSON.encode(HARRY_DUMPED)),
            ],
        ],
    )
    def test_req_load_bson_list(self, api: SpanAPI, data):
        @api.route("/test")
        class TestRoute(SpanRoute):
            @api.use_schema(req=NameSchema(many=True))
            async def on_post(self, req: Request, resp: Response):
                assert await req.media_loaded() == [HARRY, HARRY]

        with api.requests as client:
            headers = {"Content-Type": "application/bson"}
            r = client.post("/test", data=encode_bson(data), headers=headers)
            validate_response(r)

    def test_req_schema_class_marshmallow(self, api: SpanAPI):
        class NameSchemaM(marshmallow.Schema):
            id = marshmallow.fields.UUID()
            first = marshmallow.fields.Str()
            last = marshmallow.fields.Str()

        harry_loaded = NameSchemaM().load(HARRY_DUMPED)

        @api.route("/test")
        class TestRoute(SpanRoute):
            @api.use_schema(req=NameSchemaM())
            async def on_post(self, req: Request, resp: Response):
                assert await req.media_loaded() == harry_loaded

        with api.requests as client:
            r = client.post("/test", json=HARRY_DUMPED)
            validate_response(r)

    def test_req_load_text(self, api: SpanAPI):
        @api.route("/test")
        class TestRoute(SpanRoute):
            @api.use_schema(req=MimeType.TEXT)
            async def on_post(self, req: Request, resp: Response):
                assert await req.media_loaded() == "test_text"

        with api.requests as client:
            r = client.post("/test", data="test_text")
            validate_response(r)

    def test_error_not_a_json(self, api: SpanAPI):
        @api.route("/test")
        class TestRoute(SpanRoute):
            @api.use_schema(req=NameSchema())
            async def on_post(self, req: Request, resp: Response):
                await req.media()

        with api.requests as client:
            r = client.post("/test", data=bytes(14))
            validate_error(r, errors_api.RequestValidationError)
コード例 #25
0
class TestRawBSONDocument(unittest.TestCase):

    # {u'_id': ObjectId('556df68b6e32ab21a95e0785'),
    #  u'name': u'Sherlock',
    #  u'addresses': [{u'street': u'Baker Street'}]}
    bson_string = (
        b'Z\x00\x00\x00\x07_id\x00Um\xf6\x8bn2\xab!\xa9^\x07\x85\x02name\x00\t'
        b'\x00\x00\x00Sherlock\x00\x04addresses\x00&\x00\x00\x00\x030\x00\x1e'
        b'\x00\x00\x00\x02street\x00\r\x00\x00\x00Baker Street\x00\x00\x00\x00'
    )
    document = RawBSONDocument(bson_string)

    @classmethod
    def setUpClass(cls):
        cls.client = client_context.client

    def tearDown(self):
        if client_context.connected:
            self.client.pymongo_test.test_raw.drop()

    def test_decode(self):
        self.assertEqual('Sherlock', self.document['name'])
        first_address = self.document['addresses'][0]
        self.assertIsInstance(first_address, RawBSONDocument)
        self.assertEqual('Baker Street', first_address['street'])

    def test_raw(self):
        self.assertEqual(self.bson_string, self.document.raw)

    @client_context.require_connection
    def test_round_trip(self):
        db = self.client.get_database(
            'pymongo_test',
            codec_options=CodecOptions(document_class=RawBSONDocument))
        db.test_raw.insert_one(self.document)
        result = db.test_raw.find_one(self.document['_id'])
        self.assertIsInstance(result, RawBSONDocument)
        self.assertEqual(dict(self.document.items()), dict(result.items()))

    def test_with_codec_options(self):
        # {u'date': datetime.datetime(2015, 6, 3, 18, 40, 50, 826000),
        #  u'_id': UUID('026fab8f-975f-4965-9fbf-85ad874c60ff')}
        # encoded with JAVA_LEGACY uuid representation.
        bson_string = (
            b'-\x00\x00\x00\x05_id\x00\x10\x00\x00\x00\x03eI_\x97\x8f\xabo\x02'
            b'\xff`L\x87\xad\x85\xbf\x9f\tdate\x00\x8a\xd6\xb9\xbaM'
            b'\x01\x00\x00\x00')
        document = RawBSONDocument(bson_string,
                                   codec_options=CodecOptions(
                                       uuid_representation=JAVA_LEGACY,
                                       document_class=RawBSONDocument))

        self.assertEqual(uuid.UUID('026fab8f-975f-4965-9fbf-85ad874c60ff'),
                         document['_id'])

    @client_context.require_connection
    def test_round_trip_codec_options(self):
        doc = {
            'date': datetime.datetime(2015, 6, 3, 18, 40, 50, 826000),
            '_id': uuid.UUID('026fab8f-975f-4965-9fbf-85ad874c60ff')
        }
        db = self.client.pymongo_test
        coll = db.get_collection(
            'test_raw',
            codec_options=CodecOptions(uuid_representation=JAVA_LEGACY))
        coll.insert_one(doc)
        raw_java_legacy = CodecOptions(uuid_representation=JAVA_LEGACY,
                                       document_class=RawBSONDocument)
        coll = db.get_collection('test_raw', codec_options=raw_java_legacy)
        self.assertEqual(
            RawBSONDocument(BSON.encode(doc, codec_options=raw_java_legacy)),
            coll.find_one())

    @client_context.require_connection
    def test_raw_bson_document_embedded(self):
        doc = {'embedded': self.document}
        db = self.client.pymongo_test
        db.test_raw.insert_one(doc)
        result = db.test_raw.find_one()
        self.assertEqual(BSON(self.document.raw).decode(), result['embedded'])

        # Make sure that CodecOptions are preserved.
        # {'embedded': [
        #   {u'date': datetime.datetime(2015, 6, 3, 18, 40, 50, 826000),
        #    u'_id': UUID('026fab8f-975f-4965-9fbf-85ad874c60ff')}
        # ]}
        # encoded with JAVA_LEGACY uuid representation.
        bson_string = (
            b'D\x00\x00\x00\x04embedded\x005\x00\x00\x00\x030\x00-\x00\x00\x00'
            b'\tdate\x00\x8a\xd6\xb9\xbaM\x01\x00\x00\x05_id\x00\x10\x00\x00'
            b'\x00\x03eI_\x97\x8f\xabo\x02\xff`L\x87\xad\x85\xbf\x9f\x00\x00'
            b'\x00')
        rbd = RawBSONDocument(bson_string,
                              codec_options=CodecOptions(
                                  uuid_representation=JAVA_LEGACY,
                                  document_class=RawBSONDocument))

        db.test_raw.drop()
        db.test_raw.insert_one(rbd)
        result = db.get_collection(
            'test_raw',
            codec_options=CodecOptions(
                uuid_representation=JAVA_LEGACY)).find_one()
        self.assertEqual(rbd['embedded'][0]['_id'],
                         result['embedded'][0]['_id'])

    @client_context.require_connection
    def test_write_response_raw_bson(self):
        coll = self.client.get_database(
            'pymongo_test',
            codec_options=CodecOptions(
                document_class=RawBSONDocument)).test_raw

        # No Exceptions raised while handling write response.
        coll.insert_one(self.document)
        coll.delete_one(self.document)
        coll.insert_many([self.document])
        coll.delete_many(self.document)
        coll.update_one(self.document, {'$set': {'a': 'b'}}, upsert=True)
        coll.update_many(self.document, {'$set': {'b': 'c'}})
コード例 #26
0
    def _test_auto_encrypt(self, opts):
        client = rs_or_single_client(auto_encryption_opts=opts)
        self.addCleanup(client.close)

        # Create the encrypted field's data key.
        key_vault = self.client.admin.get_collection('datakeys',
                                                     codec_options=OPTS)
        data_key = RawBSONDocument(
            bson_data('custom', 'key-document-local.json'))
        key_vault.insert_one(data_key)
        self.addCleanup(key_vault.drop)

        # Collection.insert_one/insert_many auto encrypts.
        docs = [{
            '_id': 0,
            'ssn': '000'
        }, {
            '_id': 1,
            'ssn': '111'
        }, {
            '_id': 2,
            'ssn': '222'
        }, {
            '_id': 3,
            'ssn': '333'
        }, {
            '_id': 4,
            'ssn': '444'
        }, {
            '_id': 5,
            'ssn': '555'
        }]
        encrypted_coll = client.pymongo_test.test
        encrypted_coll.insert_one(docs[0])
        encrypted_coll.insert_many(docs[1:3])
        unack = encrypted_coll.with_options(write_concern=WriteConcern(w=0))
        unack.insert_one(docs[3])
        unack.insert_many(docs[4:], ordered=False)
        wait_until(lambda: self.db.test.count_documents({}) == len(docs),
                   'insert documents with w=0')

        # Database.command auto decrypts.
        res = client.pymongo_test.command('find',
                                          'test',
                                          filter={'ssn': '000'})
        decrypted_docs = res['cursor']['firstBatch']
        self.assertEqual(decrypted_docs, [{'_id': 0, 'ssn': '000'}])

        # Collection.find auto decrypts.
        decrypted_docs = list(encrypted_coll.find())
        self.assertEqual(decrypted_docs, docs)

        # Collection.find auto decrypts getMores.
        decrypted_docs = list(encrypted_coll.find(batch_size=1))
        self.assertEqual(decrypted_docs, docs)

        # Collection.aggregate auto decrypts.
        decrypted_docs = list(encrypted_coll.aggregate([]))
        self.assertEqual(decrypted_docs, docs)

        # Collection.aggregate auto decrypts getMores.
        decrypted_docs = list(encrypted_coll.aggregate([], batchSize=1))
        self.assertEqual(decrypted_docs, docs)

        # Collection.distinct auto decrypts.
        decrypted_ssns = encrypted_coll.distinct('ssn')
        self.assertEqual(decrypted_ssns, [d['ssn'] for d in docs])

        # Make sure the field is actually encrypted.
        for encrypted_doc in self.db.test.find():
            self.assertIsInstance(encrypted_doc['_id'], int)
            self.assertEncrypted(encrypted_doc['ssn'])

        # Attempt to encrypt an unencodable object.
        with self.assertRaises(BSONError):
            encrypted_coll.insert_one({'unencodeable': object()})
コード例 #27
0
 async def on_get(self, req: Request, resp: Response):
     resp.media = RawBSONDocument(BSON.encode(HARRY_DUMPED))