Construyendo un complemento escalable de favores de Wordpress: una matriz de valor meta serializada o muchos metaretales

4

Estoy intentando crear un complemento de publicación favorita de Wordpress que sea escalable y pueda manejar miles o miles de usuarios o más.

He visto varios enfoques diferentes en otros complementos y me gustaría saber cuál sería la mejor práctica desde el punto de vista de la escalabilidad, lo que significa que el tamaño del registro o el número de registros podría ser un problema.

Problema: la idea básica es que hay un botón en una publicación en el que un usuario que ha iniciado sesión puede hacer clic para agregar a favoritos la publicación. Luego, esto debe almacenarse en la base de datos para que cuando el usuario vaya a esa publicación, no pueda volver a marcarla como favorita y también pueda ver una lista de sus publicaciones favoritas.

Opción 1: Almacene en las tablas meta y post meta de usuario con matrices serializadas

Esto es lo que hace Wordpress Post Like System ( enlace ). Después del clic, el código recupera la clave meta _liked_posts de la meta tabla del usuario que almacena en una matriz los identificadores de publicación de las publicaciones que le han gustado al usuario y recupera la clave meta _user_likes de la meta tabla posterior que almacena en una matriz que el usuario ID de los usuarios a los que les ha gustado la publicación.

El código luego agrega la identificación de la publicación actual a _liked_posts y la identificación de usuario actual a _user_likes. También incrementa otros dos meta registros: publicar como conteo y un usuario como conteo.

Lo que me gusta de este sistema es que parece bastante simple, con solo un registro en la meta del usuario y un registro en el almacenamiento de metadatos posteriores a quien le ha gustado qué. Lo que no me gusta es que si a muchos usuarios les gusta la publicación o a un usuario a quien le gustan muchas publicaciones, esos arreglos de valores meta podrían ser muy largos, lo que supongo que podría causar problemas.

$meta_POSTS = get_user_meta( $user_id, "_liked_posts" ); // post ids from user meta
$meta_USERS = get_post_meta( $post_id, "_user_liked" ); // user ids from post meta
$meta_POSTS['post-'.$post_id] = $post_id; // Add post id to user meta array
$meta_USERS['user-'.$user_id] = $user_id; // add user id to post meta array
update_post_meta( $post_id, "_user_liked", $meta_USERS ); // Add user ID to post meta
update_user_meta( $user_id, "_liked_posts", $meta_POSTS ); // Add post ID to user meta

Opción 2: agregue un registro al meta del usuario para cada publicación que le guste

Tras el clic, el código comprueba si ya se ha insertado un registro en el meta del usuario. Si no, agrega un nuevo registro del favorito. Si lo ha hecho, no hace nada.

Lo que me gusta de este sistema, es que es fácil de consultar y generar estadísticas en el futuro, ya que no está vinculado a matrices en serie. Lo que no me gusta es que si le gusta al usuario muchas publicaciones, podría aumentar enormemente el número de registros en la tabla de metadatos del usuario.

// Check if already favourited the post in User Meta
// Not sure how you would do this with WP_Query or WP_User_Query, any suggestions?

$favourited = WP_Query($args)

if ($favourited->post_count == 0) {
  // Add user meta with favourite
  add_user_meta($userid, '_favourite_episode', $postid);
}

Para concluir, lo que estoy preguntando esencialmente es qué es la mejor práctica aquí. ¿Está bien?

  • Tener una matriz serializada grande en un solo par de clave / valor meta
  • Tener muchos pares de valores meta / clave con un entero en el valor meta
  • ¿Hay otra opción que no haya considerado?

EDITAR: Después de las respuestas proporcionadas, he decidido que crear una tabla personalizada es la mejor manera de avanzar. He encontrado este tutorial que hace casi lo que quiero hacer y de una manera mucho más ampliable para que pueda agregar otras acciones, así como simplemente 'favouriting'.

enlace

    
pregunta Alex 03.04.2016 - 17:39

2 respuestas

4

Olvidó la opción 3: agregue una tabla especial en la que el par (usuario, post id) será el índice. Ok, no soy una persona de MySQL, así que quizás sea demasiado extremo, pero tal vez tener dos tablas, una con los usuarios como índice y otra con las publicaciones, será aún mejor.

Lo que pasa con el rendimiento es que rara vez hay soluciones absolutas para todos en cualquier momento, y lo "mejor" depende de su patrón de uso real, no del teórico. O en otras palabras, estás haciendo una optimización temprana aquí.

Si bien la opción 2 parece ser más rápida para esta información específica, hará que las meta tablas sean más grandes y, por lo tanto, es probable que disminuya la velocidad de todas a esas tablas (por lo tanto, la sugerencia para la opción 3 es muy similar pero no afecta a otras consultas).

Otro problema que ignora aquí es el costo de la inserción / actualización de datos. Esta operación es mucho más lenta que una lectura y no se puede almacenar en caché. Si va a tener muchos "me gusta" al mismo tiempo, con la opción 2 bloqueará las tablas y las solicitudes deberán esperar a que otros se completen y cada inserción será más lenta, mientras que la opción 1 terminará en corrupción de datos en una implementación ingenua (dos cambios al mismo tiempo, en el mejor de los casos, solo uno de ellos tendrá impacto).

Y luego debes tener en cuenta qué tipo de almacenamiento en caché harás. Con un buen esquema de almacenamiento en caché, el tiempo de lectura no es un problema.

Para concluir, deseo que encuentre que este es un problema real que debe resolverse, hasta entonces simplemente escriba la api adecuada para acceder / cambiar los datos para ocultar los detalles de la implementación, de modo que si se convierta en un problema, usted sea capaz de cambiar la implementación sin afectar el resto de su código.

    
respondido por el Mark Kaplun 03.04.2016 - 18:21
0
La

Opción 1 no es la mejor opción porque serializar los datos significa que debe analizar el resultado de SQL para que sea legible y, por lo tanto, no puede aprovechar las ventajas de las consultas SQL.

La

Opción 2 sería la forma más fácil, pero si tienes muchos usuarios que gustan de muchas publicaciones, entonces comienza a contaminar la meta tabla de usuarios.

Opción 3 Lo que haría es crear una tabla relacional entre las publicaciones y los usuarios. Usar la tabla de relaciones sería lo más fácil porque entonces puede usar SQL para hacer mucha lógica por usted. Por ejemplo, no necesita contar cuántos "me gusta" tiene una publicación en PHP, sino ejecutar una consulta contra SQL que lo haga por usted y devuelva el resultado. Lo que significa que será bueno para el rendimiento y si desinstala el complemento, todo lo que tiene que hacer es eliminar la tabla, simple y limpia.

    
respondido por el Marttin Notta 03.04.2016 - 17:54

Lea otras preguntas en las etiquetas