sql >> Base de Datos >  >> NoSQL >> MongoDB

pymongo.errors.CursorNotFound:la identificación del cursor '...' no es válida en el servidor

Recibe este error porque el cursor se está agotando en el servidor (después de 10 minutos de inactividad).

De la documentación de pymongo:

Los cursores en MongoDB pueden agotar el tiempo de espera en el servidor si han estado abiertos durante mucho tiempo sin que se haya realizado ninguna operación en ellos. Esto puede conducir a que se genere una excepción CursorNotFound al intentar iterar el cursor.

Cuando llamas a collection.find método consulta una colección y devuelve un cursor a los documentos. Para obtener los documentos, itera el cursor. Cuando itera sobre el cursor, el controlador en realidad está haciendo solicitudes al servidor MongoDB para obtener más datos del servidor. La cantidad de datos devueltos en cada solicitud se establece mediante batch_size() método.

De la documentación:

Limita el número de documentos devueltos en un lote. Cada lote requiere un viaje de ida y vuelta al servidor. Se puede ajustar para optimizar el rendimiento y limitar la transferencia de datos.

Establecer el tamaño de lote en un valor más bajo lo ayudará con los errores de tiempo de espera, pero aumentará la cantidad de veces que tendrá acceso al servidor MongoDB para obtener todos los documentos.

El tamaño de lote predeterminado:

Para la mayoría de las consultas, el primer lote devuelve 101 documentos o solo los documentos suficientes para superar 1 megabyte. El tamaño del lote no excederá el tamaño máximo del documento BSON (16 MB).

No existe un tamaño de lote "correcto" universal. Debe probar con diferentes valores y ver cuál es el valor apropiado para su caso de uso, es decir, cuántos documentos puede procesar en una ventana de 10 minutos.

El último recurso será que establezca no_cursor_timeout=True . Pero debe asegurarse de que el cursor esté cerrado después de terminar de procesar los datos.

Cómo evitarlo sin try/except :

cursor = collection.find(
     {"x": 1},
     no_cursor_timeout=True
)
for doc in cursor:
    # do something with doc
cursor.close()