コード例 #1
0
ファイル: tools.py プロジェクト: Ladder-Climbers/mayne-code
def get_next_id(col: pymongo.collection.Collection, id_name: str):
    # logger.warning(f'id_name: {id_name}')
    ret = col.find_one_and_update({"_id": id_name},
                                  {"$inc": {"sequence_value": 1}},
                                  new=True)
    new_id = ret["sequence_value"]
    return new_id
コード例 #2
0
def update_user_document(coll: pymongo.collection.Collection,
                         user_id: ObjectId, document_id: ObjectId,
                         document: dict):
    assert isinstance(user_id, ObjectId)
    assert isinstance(document_id, ObjectId)

    to_set, to_unset = get_mdocument_set_unset_dicts(document)

    operation_dict = {}
    if to_set:  # některý z fieldů je neprázdný
        operation_dict["$set"] = {
            f"documents.$.{key}": value
            for key, value in to_set.items()
        }
    if to_unset:
        operation_dict["$unset"] = {
            f"documents.$.{key}": value
            for key, value in to_unset.items()
        }

    assert not (set(to_set.keys()).intersection(set(to_unset.keys())))
    print("to_set", to_set)
    print("to_unset", to_unset)

    updated = coll.find_one_and_update(
        {
            "_id": user_id,
            "documents._id": document_id
        },
        operation_dict,
        return_document=ReturnDocument.AFTER)
    if not list(updated):
        raise ValueError("Uživatel nemá dokument s tímto _id")
コード例 #3
0
def import_new_records(base_id: str,
                       table: str,
                       mongo_table: pymongo.collection.Collection,
                       view: Optional[str] = None) -> None:
    """Import new records from Airtable to MongoDB."""

    if not _AIRTABLE_API_KEY:
        raise ValueError(
            'No API key found. Create an airtable API key at '
            'https://airtable.com/account and set it in the AIRTABLE_API_KEY '
            'env var.')
    client = airtable.Airtable(base_id, _AIRTABLE_API_KEY)
    records = client.iterate(table, view=view)

    converter = airtable_to_protos.ProtoAirtableConverter(
        proto_type=review_pb2.DocumentToReview,
        id_field=None,
        required_fields=('anonymized_url', ))

    num_inserted = 0
    num_updated = 0
    for record in records:
        mongo_id = record.get('fields', {}).get('mongo_id')

        proto_data = converter.convert_record(record)
        airtable_id = proto_data.pop('_id')
        if record['fields'].get('anonymized_url'):
            proto_data['anonymizedUrl'] = record['fields']['anonymized_url'][
                0]['url']

        if mongo_id:
            # Already added, let's update it.
            document_json = mongo_table.find_one_and_update(
                {'_id': objectid.ObjectId(mongo_id)},
                {'$set': proto_data},
            )
            any_pending_or_done_review = document_json.get('numPendingReviews', 0) or \
                document_json.get('numDoneReviews', 0)
            timeout_review_count = sum(
                1 for review in document_json.get('reviews', [])
                if review.get('status') == 'REVIEW_TIME_OUT')
            client.update(
                table, airtable_id, {
                    'Bayes help needed': not any_pending_or_done_review,
                    'review_timeouts': timeout_review_count,
                })
            num_updated += 1
            continue

        result = mongo_table.insert_one(proto_data)
        mongo_id = str(result.inserted_id)
        client.update(table, airtable_id, {
            'mongo_id': mongo_id,
            'Bayes help needed': True
        })
        num_inserted += 1

    print(f'{num_updated:d} documents updated.')
    print(f'{num_inserted:d} documents added.')
コード例 #4
0
def update_user_address(coll: pymongo.collection.Collection, user_id: ObjectId,
                        address: dict):
    assert isinstance(user_id, ObjectId)

    address_type = address["type"]

    to_set, to_unset = get_mdocument_set_unset_dicts(address)

    # pokud už je tento typ adresy v databázi
    if coll.find_one({"_id": user_id, "addresses.type": address_type}):

        operation_dict = {}
        if len(to_set) > 1:  # je tam něco kromě "type"
            operation_dict["$set"] = {
                f"addresses.$.{key}": value
                for key, value in to_set.items()
            }
        if to_unset:
            operation_dict["$unset"] = {
                f"addresses.$.{key}": value
                for key, value in to_unset.items()
            }

        updated = coll.find_one_and_update(
            {
                "_id": user_id,
                "addresses.type": address_type
            },
            operation_dict,
            return_document=ReturnDocument.AFTER)

        # smaž adresu z "addresses", pokud po updatu obsahuje pouze "type"
        for address in updated["addresses"]:
            if address["type"] == address_type and len(address) <= 1:
                delete_user_address(coll, user_id, address_type)

    # jinak přidej adresu do databáze, pokud obsahuje víc než jen "type"
    elif len(address) > 1:
        add_embedded_mdoc_to_mdoc_array(coll,
                                        user_id,
                                        "addresses",
                                        address,
                                        filter_values=None)
コード例 #5
0
def update_user(coll: pymongo.collection.Collection,
                user_id: ObjectId,
                data: dict,
                embedded_1to1_docs=("name", )):
    assert isinstance(user_id, ObjectId)

    to_unset = {key: "" for key, value in data.items() if value == ""}
    for key in to_unset:
        del data[key]

    operation_dict = {}
    if data:
        operation_dict["$set"] = data
    if to_unset:
        operation_dict["$unset"] = to_unset

    updated = coll.find_one_and_update({"_id": user_id},
                                       operation_dict,
                                       return_document=ReturnDocument.AFTER)

    for key in embedded_1to1_docs:
        if key in updated and not updated[key]:
            coll.update_one({"_id": user_id}, {"$unset": {"name": ""}})