Zicsus
Estaba usando la base de datos en tiempo real de Firebase para mi aplicación de red social donde puedes seguir y recibir publicaciones de las personas que sigues.
Mi base de datos:
Users
--USER_ID_1
----name
----email
--USER_ID_2
----name
----email
Posts
--POST_ID_1
----image
----userid
----date
--POST_ID_2
----image
----userid
----date
Timeline
--User_ID_1
----POST_ID_2
------date
----POST_ID_1
------date
Otro nodo “Contenido” contenía la identificación de todas las publicaciones de los usuarios. Si “A” siguió a “B”, entonces todas las identificaciones de publicaciones de B se agregaron a la línea de tiempo de A. Y si B publicó algo, también se agrega a todas las líneas de tiempo de sus seguidores.
Tiene problemas de escalabilidad:
- Si alguien tiene 10.000 seguidores, se agrega una nueva publicación a las líneas de tiempo de los 10.000 seguidores.
- Si alguien tiene una gran cantidad de publicaciones, cada nuevo seguidor las recibe todas en su línea de tiempo.
Quiero cambiar a Firestore ya que se ha afirmado que es escalable. ¿Cómo debo estructurar mi base de datos para que estos problemas en la base de datos en tiempo real se eliminen en Firestore?
-
Dirigir a los usuarios a otras publicaciones tuyas semi-relevantes no es una respuesta. Tampoco me gusta su enfoque para recuperar un feed. Un feed típico no devolvería solo las publicaciones de 15 usuarios. En cambio, miran todas las publicaciones cronológicamente. Entonces, no creo que sea una buena respuesta, incluso con su longitud/detalle, creo que no da en el blanco.
– Thingamajig
7 junio 2019 a las 15:21
-
@Soorya Siempre costará la cantidad exacta de operaciones que realice. Nada mas.
– Alex Mamo
6 de mayo de 2020 a las 8:18
-
@Soorya También compruebas este afuera.
– Alex Mamo
7 de mayo de 2020 a las 7:22
-
@ernewston Gracias. Sí, puede ser una solución siempre y cuando resuelva tu problema. Pero recuerde, siempre es un intercambio cuando se trata de duplicación de datos. Deberías hacer algunas pruebas y comprobar si merece la pena o no.
– Alex Mamo
26 de mayo de 2020 a las 9:13
-
@AlexMamo gracias por la respuesta. Hasta ahora esta es la mejor solución. Pero calculé el costo de escribir en la línea de tiempo de cada usuario, se vuelve enorme. Considere 2K DAU y cada usuario activo tiene 1K seguidores en promedio, siguen a 10 personas nuevas / día y publican 10 nuevas / día. Cada nueva persona a la que siguen tiene una media de ~500 publicaciones. Y cada DAU tiene 1K seguidores en promedio. Entonces, cuando siguen a una persona nueva: 2K*10*500/día de escrituras, cuando publican: 2K*10*1K/día. Luego todos x30 días. Luego, menos la cuota gratuita, todavía tenemos que pagar $1,618. Solo para escribir el conteo. se llevó el 80% de la facturación. ¿Alguna manera mejor?
– Zenko
2 de julio de 2020 a las 20:50
-
@Niyas Con esta solución, si el usuario A sigue al usuario B que tiene reseñas de B_r, realizaremos escrituras de B_r para cada seguimiento, ¿correcto?
– thedeg123
30 de abril de 2020 a las 15:34
-
Usted dijo
you must add the list of followers in post document.
pero aquí está el gran problema con esa solución: cuando un usuario obtiene un nuevo seguidor y tiene 10k publicaciones, debe actualizar cada una de esas 10k publicaciones para agregar este nuevo seguidor en la matriz de seguidores. 10k escribe para 1 seguimiento. Eso no suena como una buena arquitectura.– Antoine Weber
11 oct 2020 a las 2:30
-
Sin embargo, debo decir que esta parece ser la mejor respuesta, aunque no es ideal.
– Antoine Weber
11 oct 2020 a las 15:52
-
Usé su respuesta como base para mi solicitud y ha funcionado maravillosamente. Superé el límite de la matriz con su sugerencia del indicador ‘hasNext’ y luego dupliqué la publicación para cada documento adicional que contiene una matriz de los siguientes usuarios. @Antoine Tomaría el caso extremo de duplicar 10k publicaciones en lugar de duplicar una publicación para 1 millón de seguidores
– cpboyce
21 de abril de 2021 a las 18:54
-
Esta es la forma más eficiente, hasta ahora, de crear una línea de tiempo cronológica de las publicaciones de diferentes usuarios. Ojalá pudiera votar 10 veces para que la gente sepa que esta es una buena respuesta.
– Tadreik
5 de diciembre de 2021 a las 17:18
-
@Tadreik ¡Gracias! Estábamos sufriendo problemas de escala y se me ocurrió esto. Lo hemos usado en producción durante más de un año sin problemas.
–Albert Renshaw
7 de diciembre de 2021 a las 2:41
-
me gusta el
recentPostsLastUpdatedAt
además, tiene mucho sentido para reducir el espacio de búsqueda de consulta del usuario.– LordPerejil
7 ene a las 12:22
-
Parece la mejor opción aquí en lo que respecta a la optimización de costos. Probaré esto, pero experimentaré almacenando en caché el
recentPosts
matriz a los navegadoreslocalStorage
. Luego, actualice el caché usando una consulta que solo obtiene los documentos de usuariorecentPosts
dónderecentPostLastUpdated
es más reciente que la última publicación “más reciente” en el caché. Otra cosa con la que experimentar es con qué frecuencia consultar nuevas publicaciones, mientras el usuario está en la página. Además, no actualizar el feed mientras la pestaña/página no está activa podría ser útil, supongo…– Espiral
17 de septiembre a las 0:37
-
Muy buena solución, definitivamente lo intentaré. Sin embargo, tengo una pregunta. Dijiste: “Al cargar los documentos de usuario, puedes agruparlos 10 a la vez usando la consulta in… normalmente esto no haría ninguna diferencia porque todavía son 10 lecturas a pesar de que están agrupadas…”. ¿Podrías explicar esto más a fondo? No estoy seguro de lo que quieres decir con eso? Gracias 🙂
– Jorge
4 de noviembre a las 10:55
Descargo de responsabilidad: solo estoy listo a través de los documentos de firestore. Como firestore tiene una consulta mucho mejor que firebase-realtime-db, ya no necesita copiar datos. Entonces, lo que haría es: cuando un usuario mira su línea de tiempo, crea una consulta de Firestore que dice
give me all posts which are from the people i follow
. Algo como: posts.where(user== john OR mark OR katy OR…). Espero que algo como esto funcione. En caso de que tenga tiempo de probarlo os lo comento.– Jürgen Brandstetter
16 de noviembre de 2017 a las 11:21
@jurgenBrandstetter Firestore no admite ‘O’ en este momento y, si lo hiciera, su método tampoco funcionará. supongamos que alguien tiene 1000 seguidores que yo tengo que hacer 1000 declaraciones OR.
– Zicsus
18 de noviembre de 2017 a las 4:35
Estaba pensando, puede ser si pones en tu documento la identificación de la persona que te está siguiendo. Por ejemplo, UserA sigue a UserB, luego, en el documento de publicación de UserB, coloca UserAID = true. Entonces, cuando haga la consulta, será algo así como == postDocRef.where (UserAID = true), pero no sé si un documento en firestore puede admitir hasta un millón de seguidores.
– Giovanny Piñeros
18 mayo 2018 a las 19:14
@Zicsus Supongamos este ejemplo. Hice 10 000 publicaciones. Ahora me estás siguiendo. Puede ordenar las publicaciones por marca de tiempo y luego limitarlas a una cierta cantidad, por ejemplo, 15 publicaciones y usar el método .childAdded. Para cargar más datos en el mismo orden cronológico, podría crear un método con un observador de tipo: ObserveSingleEvent(ofType:Value) con un límite de 10 publicaciones. Luego implemente una función de extracción para actualizar en su vista de tabla o use el desplazamiento de vista de desplazamiento y cuando llegue al final de la tabla, simplemente llame a su
ObserveSingleEvent
método y obtener más elementos y así sucesivamente.– babero
29 de agosto de 2018 a las 18:07
@bibscy La pregunta no se trata de preparar un feed si solo sigues a una persona, sino de cómo preparar un feed cronológico como Twitter, donde ves las actividades de todos los usuarios que sigues.
– Zicsus
29 de agosto de 2018 a las 18:20