{"id":229184,"date":"2022-11-05T16:50:00","date_gmt":"2022-11-05T13:50:00","guid":{"rendered":"https:\/\/wordpress.mediadoma.com\/?p=229184"},"modified":"2022-11-09T05:51:50","modified_gmt":"2022-11-09T02:51:50","slug":"mejoras-en-la-legibilidad-de-wp_query-para-mantenimiento","status":"publish","type":"post","link":"https:\/\/wordpress.mediadoma.com\/es\/mejoras-en-la-legibilidad-de-wp_query-para-mantenimiento\/","title":{"rendered":"Mejoras en la legibilidad de WP_Query (para mantenimiento)"},"content":{"rendered":"\n<p>Trabajar con <a href=\"https:\/\/tommcfarlin.com\/passing-variables-in-wordpress-wp-query\/\" target=\"_blank\" rel=\"noopener nofollow\" class=\"external external_icon\">WP_Query<\/a>, especialmente cuando est\u00e1 haciendo un trabajo personalizado fuera del habitual &quot;obtener algunas publicaciones y mostrarlas en una plantilla&quot;, puede ser poderoso. Esto es especialmente cierto para algunos de los argumentos avanzados (como usar <a href=\"https:\/\/codex.wordpress.org\/Class_Reference\/WP_Meta_Query\" target=\"_blank\" rel=\"noopener nofollow\" class=\"external external_icon\">WP_Meta_Query<\/a>, por ejemplo) .<\/p>\n<p>Tambi\u00e9n es bueno que la configuraci\u00f3n del proceso tenga una forma est\u00e1ndar de hacer las cosas. A saber:<\/p>\n<ol>\n<li>Definir los argumentos,<\/li>\n<li>Instanciar WP_Query,<\/li>\n<li>Compruebe si hay publicaciones,<\/li>\n<li>Bucle a trav\u00e9s de ellos,<\/li>\n<li><a href=\"https:\/\/www.youtube.com\/watch?v=g2JNxeWO_wA\" target=\"_blank\" rel=\"noopener nofollow\" class=\"external external_icon\">Terminarlos<\/a>.<\/li>\n<\/ol>\n<div class=\"sds-iframe-wrapper fitvidsignore\" style=\"position:relative;padding-top:56.25%;max-width:100%;\"><iframe allowfullscreen style=\"position:absolute;top:0;left:0;width:100%;height:100%;\" src=\"\/\/www.youtube.com\/embed\/g2JNxeWO_wA\" frameborder=\"0\"><\/iframe><\/div>\n<p>Pero si llega a donde est\u00e1 haciendo un trabajo avanzado, como trabajar con un tipo de publicaci\u00f3n personalizada de una soluci\u00f3n de terceros, tener que descargar medios, determinar si existe algo antes de trabajar con \u00e9l, entonces puede ser un un poco m\u00e1s complicado para trabajar, \u00bfno?<\/p>\n<p>Descubr\u00ed que, como con cualquier cosa en la programaci\u00f3n, dividirlo en m\u00f3dulos mucho m\u00e1s legibles (o funciones o piezas o como quiera llamarlos) puede hacer que sea mucho m\u00e1s f\u00e1cil trabajar con ellos.<\/p>\n<p>As\u00ed que aqu\u00ed hay una forma en que trabajo para mejorar la legibilidad de WP_Query en una variedad de cosas que he hecho \u00faltimamente.<\/p>\n<h2>Mejoras en la legibilidad de WP_Query<\/h2>\n<p>Antes de analizar cualquier ejemplo, vale la pena se\u00f1alar que hay algunas cosas que la forma en que WP_Query est\u00e1 configurado que no podemos hacer.<\/p>\n<p>Por ejemplo, una vez que se crea una instancia de la consulta, es posible que no podamos hacer cosas mucho m\u00e1s avanzadas con ella (es decir, configurar cualquier prueba unitaria que no requiera el n\u00facleo de WordPress va a ser imposible).<\/p>\n<p>Esta es la cara de alguien que no puede seguir tu c\u00f3digo.<\/p>\n<p>Dicho esto, aqu\u00ed hay un ejemplo de c\u00f3mo puede verse cuando comienza y luego c\u00f3mo se puede refactorizar para tener funciones m\u00e1s peque\u00f1as, cada una de las cuales es m\u00e1s intencional que un m\u00e9todo largo.<\/p>\n<h3>Un ejemplo<\/h3>\n<p>Para esta publicaci\u00f3n, digamos que necesito consultar la base de datos para todas las publicaciones y publicaciones publicadas y quiero ordenarlas por ID.<\/p>\n<p>A continuaci\u00f3n, quiero determinar si alguna herramienta de terceros le asign\u00f3 algunos metadatos que corresponden a una plantilla que luego puedo asignar mediante programaci\u00f3n dado un tema que tengo.<\/p>\n<p>Quiz\u00e1s la versi\u00f3n inicial del c\u00f3digo podr\u00eda verse <a href=\"https:\/\/gist.github.com\/tommcfarlin\/90b954c3afde140c8573d1934172537f#file-00-wp-query-php\" target=\"_blank\" rel=\"noopener nofollow\" class=\"external external_icon\">as\u00ed<\/a> :<\/p>\n<pre><code>&lt;?php\n\n\/\/ Assume this is defined within the context of a class.\nconst MAPPING = [\n        'employers'       =&gt; 'page-past-word.php',\n        'biography'       =&gt; 'page-biography.php',\n        'accomplishments' =&gt; 'page-csv.php',\n    ];\n\n\/* Snip the rest of the class for brevity *\/\n\npublic function map_templates() {\n\n  $args = [\n    'post_type'      =&gt; array( 'post', 'page' ),\n    'post_status'    =&gt; 'publish',\n    'orderby'        =&gt; 'ID',\n    'order'          =&gt; 'ASC',\n    'posts_per_page' =&gt; -1,\n  ];\n  $template_query = new WP_Query( $args );\n\n    if ($template_query-&gt;have_posts()) {\n        while ($template_query-&gt;have_posts()) {\n            $template_query-&gt;the_post();\n\n            $template_id = get_post_meta( $post_id, 'third_party_template_id', true );\n            if ('' === $template_id) {\n                continue;\n            }\n\n                \/\/ The third-party's template post name can be used to map our custom template.\n            $template_info = get_post( $template_id );\n            $template_name = $template_info-&gt;post_name;\n\n            if (isset( self::MAPPING[ $template_name ])) {\n\n                $template_file = self::MAPPING[ $template_name ];\n                update_post_meta( $post_id, '_wp_page_template', $template_file );\n            }\n        }\n    }\n}\n<\/code><\/pre>\n<p>Eso es mucho c\u00f3digo para hacer bastante trabajo para una funci\u00f3n. Como m\u00ednimo, establece todo lo que debe suceder, \u00bfno es as\u00ed?<\/p>\n<p>Antes de seguir leyendo, tenga en cuenta que la matriz de mapeo es solo un ejemplo, pero las claves representan la clave meta para <strong>mapearlo<\/strong>, y eso nos ayuda a mapear la definici\u00f3n del\u00a0 valor <strong>_wp_page_template<\/strong> cuando llega el momento de mapearlo a los archivos de plantilla de WordPress reales.<\/p>\n<p>Entonces, \u00bfc\u00f3mo se puede descomponer esto?<\/p>\n<h3>1 Patea todo el asunto<\/h3>\n<p>Lo primero que queremos hacer es crear una funci\u00f3n que ponga todo en movimiento. Hay algunas maneras que puede elegir para hacer esto.<\/p>\n<p>As\u00ed es como he optado <a href=\"https:\/\/gist.github.com\/tommcfarlin\/90b954c3afde140c8573d1934172537f#file-01-map-page-templates-php\" target=\"_blank\" rel=\"noopener nofollow\" class=\"external external_icon\">por hacerlo<\/a> :<\/p>\n<pre><code>&lt;?php\n\npublic function map_page_templates() {\n\n  $posts = $this-&gt;load_posts_and_pages();\n  if ($posts-&gt;have_posts()) {\n    $this-&gt;assign_templates( $posts );\n  }\n}<\/code><\/pre>\n<p>En pocas palabras, usar\u00e1 algunas funciones auxiliares, todas las cuales documentar\u00e9 a continuaci\u00f3n, y luego asignar\u00e1 las plantillas que tengamos en la matriz de mapeo definida anteriormente.<\/p>\n<h3>2 Cargar publicaciones y p\u00e1ginas<\/h3>\n<p>Naturalmente, lo primero que queremos hacer es configurar una funci\u00f3n para llamar que devolver\u00e1 los resultados de la consulta:<\/p>\n<pre><code>&lt;?php\n\nprivate function load_posts_and_pages() {\n\n  $args = [\n    'post_type'      =&gt; array( 'post', 'page' ),\n    'post_status'    =&gt; 'publish',\n    'orderby'        =&gt; 'ID',\n    'order'          =&gt; 'ASC',\n    'posts_per_page' =&gt; -1,\n  ];\n  $posts = new WP_Query( $args );\n\n  return $posts;\n}\n<\/code><\/pre>\n<p>Esto devuelve los resultados de la consulta. De esta manera, podemos determinar si necesitamos hacer alg\u00fan trabajo adicional que decimos en esencia en el paso anterior:<\/p>\n<pre><code>&lt;?php\n\npublic function map_page_templates() {\n\n  $posts = $this-&gt;load_posts_and_pages();\n  if ($posts-&gt;have_posts()) {\n    $this-&gt;assign_templates( $posts );\n  }\n}<\/code><\/pre>\n<p>Si no, entonces hemos terminado. De lo contrario, obviamente, seguimos adelante.<\/p>\n<h3>3 Recuperar el ID de la plantilla de terceros<\/h3>\n<p>A continuaci\u00f3n, la idea de asignar plantillas, como se muestra en el c\u00f3digo anterior, parece bastante simple, pero hay algunas cosas que debemos hacer primero:<\/p>\n<ol>\n<li>iterar a trav\u00e9s de las publicaciones,<\/li>\n<li>tome la identificaci\u00f3n de terceros de la plantilla,<\/li>\n<li>toma el nombre de la plantilla de terceros,<\/li>\n<li>asigne la plantilla de la constante de mapeo definida anteriormente en la clase.<\/li>\n<\/ol>\n<p>La iteraci\u00f3n inicial de la funci\u00f3n puede verse <a href=\"https:\/\/gist.github.com\/tommcfarlin\/90b954c3afde140c8573d1934172537f#file-03-assign-templates-php\" target=\"_blank\" rel=\"noopener nofollow\" class=\"external external_icon\">as\u00ed<\/a> :<\/p>\n<pre><code>&lt;?php\n\nprivate function assign_templates( WP_Query $posts) {\n\n  while ($posts-&gt;have_posts()) {\n    $posts-&gt;the_post();\n\n    $template_id = $this-&gt;get_template_id( get_the_ID() );\n    if ('' === $template_id) {\n      continue;\n    }\n\n    $template_name = $this-&gt;get_template_name( $template_id );\n    if (null === $template_name) {\n      continue;\n    }\n\n    $this-&gt;assign_template( get_the_ID(), $template_name );\n  }\n  wp_reset_postdata();\n}\n<\/code><\/pre>\n<p>Pero como puede ver, todav\u00eda hay funciones auxiliares que necesitan definiciones. Cosas como la capacidad de obtener la ID de la plantilla, el nombre de la plantilla y, en \u00faltima instancia, asignar la plantilla.<\/p>\n<p>Tenga en cuenta, sin embargo, que si alguna de las funciones auxiliares no devuelve un valor \u00fatil, entonces continuamos con el bucle. Esto es necesario aunque solo sea para asegurarnos de que no estamos tratando de mapear plantillas que no existen (pero creo que tambi\u00e9n hace que sea un poco m\u00e1s f\u00e1cil de leer).<\/p>\n<h3>4 Encuentre el archivo al que se asigna la ID de plantilla<\/h3>\n<p>A continuaci\u00f3n, se puede usar una peque\u00f1a funci\u00f3n para ver el ID de la plantilla de terceros y determinar si podemos asignar este valor a las p\u00e1ginas que existen <a href=\"https:\/\/gist.github.com\/tommcfarlin\/90b954c3afde140c8573d1934172537f#file-04-get-template-id-php\" target=\"_blank\" rel=\"noopener nofollow\" class=\"external external_icon\">en nuestra base de datos<\/a>.<\/p>\n<pre><code>&lt;?php\n\nprivate function get_template_id( $post_id) {\n\n  $template_id = get_post_meta( $post_id, 'third_party_template_id', true );\n  return $template_id;\n}\n<\/code><\/pre>\n<p>Si no puede, entonces podemos devolver una cadena vac\u00eda y luego hacer que la funci\u00f3n que invoc\u00f3 este cheque en particular verifique si vale la pena continuar con el ciclo que hemos definido.<\/p>\n<h3>5 Tome el nombre de la plantilla<\/h3>\n<p>Suponiendo que tenemos una ID de publicaci\u00f3n v\u00e1lida, ahora debemos <a href=\"https:\/\/gist.github.com\/tommcfarlin\/90b954c3afde140c8573d1934172537f#file-05-get-template-name-php\" target=\"_blank\" rel=\"noopener nofollow\" class=\"external external_icon\">recuperar el nombre<\/a> de la plantilla de la matriz de mapeo definida anteriormente en la publicaci\u00f3n:<\/p>\n<pre><code>&lt;?php\n\nprivate function get_template_name( $template_id) {\n\n  $template_info = get_post( $template_id );\n  $template_name = $template_info-&gt;post_name;\n\n  if (isset( self::MAPPING[ $template_name ])) {\n    return $template_name;\n  } else {\n    return null;\n  }\n}\n<\/code><\/pre>\n<p>Aqu\u00ed est\u00e1 la cuesti\u00f3n: o bien devolveremos el nombre de la plantilla, o bien devolveremos un valor nulo. Nuevamente, esto es para que podamos determinar si necesitamos continuar con el ciclo de asignaci\u00f3n de plantillas o no.<\/p>\n<h3>6 Asigne la plantilla<\/h3>\n<p>Finalmente, podemos obtener la ID de la plantilla proporcionada por el tercero y usarla para <a href=\"https:\/\/gist.github.com\/tommcfarlin\/90b954c3afde140c8573d1934172537f#file-06-assign-template-php\" target=\"_blank\" rel=\"noopener nofollow\" class=\"external external_icon\">asignarla al archivo<\/a> que hemos incluido con nuestro trabajo como se describe anteriormente en la publicaci\u00f3n:<\/p>\n<pre><code>&lt;?php\n\nprivate function assign_template( $post_id, $template_name) {\n\n  $template_file = self::MAPPING[ $template_name ];\n  update_post_meta( $post_id, '_wp_page_template', $template_file );\n}\n<\/code><\/pre>\n<p>Y as\u00ed es en \u00faltima instancia c\u00f3mo puede crear c\u00f3digo y funciones mucho m\u00e1s peque\u00f1os, m\u00e1s f\u00e1ciles de leer y m\u00e1s f\u00e1ciles de usar cuando se trabaja con consultas un poco m\u00e1s complicadas.<\/p>\n<h2>Y por lo tanto, mejoras de legibilidad<\/h2>\n<p>Para aquellos acostumbrados a escribir, leer m\u00e9todos largos o hacer las cosas de la forma en que muchos de los tutoriales en la web muestran c\u00f3mo hacer las cosas en WordPress, esto puede parecer un mont\u00f3n de c\u00f3digo sin sentido.<\/p>\n<p>Pero considera esto:<\/p>\n<ol>\n<li>Los m\u00e9todos m\u00e1s largos son m\u00e1s dif\u00edciles de leer,<\/li>\n<li>Pueden ser m\u00e1s dif\u00edciles de depurar,<\/li>\n<li>Y no descomponen el problema en partes m\u00e1s manejables.<\/li>\n<\/ol>\n<p>Claro, me encantar\u00eda dividir esto en m\u00e1s clases con sus responsabilidades, y creo que se puede hacer, pero dada la naturaleza de WP_Query, requerir\u00eda un poco m\u00e1s de trabajo.<\/p>\n<p>As\u00ed que he tratado de encontrar tantos puntos medios como sea posible.<\/p>\n<p>Si est\u00e1 trabajando con usos incluso un poco m\u00e1s avanzados de WP_Query, le recomiendo al menos considerar dividirlo en partes m\u00e1s peque\u00f1as.<\/p>\n<p>Esto ayuda a cuidar la legibilidad, potencialmente cualquier capacidad de mantenimiento, y a escribir un c\u00f3digo m\u00e1s limpio en lugar de un m\u00e9todo largo con demasiados condicionales y dependencia de una variedad de otros datos.<\/p>\n<p><div id=\"PostUnique_PostSource\" style=\"padding-top: 50px\">Fuente de grabaci\u00f3n:  <a target=\"_blank\" rel=\"noopener nofollow\" href=\"\/\/tommcfarlin.com\" class=\"external external_icon\">tommcfarlin.com<\/a><\/div><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Trabajar con la legibilidad de WP_Query puede ser un desaf\u00edo. Aqu\u00ed hay un ejemplo de c\u00f3mo analizo el uso de la API en algunos de mis propios trabajos.<\/p>\n","protected":false},"author":1,"featured_media":220946,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":"","_wp_rev_ctl_limit":""},"categories":[892,716,861],"tags":[1172,1172],"class_list":["post-229184","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-codigo","category-desarrollador","category-wordpress-2","tag-affiai-es"],"_links":{"self":[{"href":"https:\/\/wordpress.mediadoma.com\/es\/wp-json\/wp\/v2\/posts\/229184","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/wordpress.mediadoma.com\/es\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/wordpress.mediadoma.com\/es\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/wordpress.mediadoma.com\/es\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/wordpress.mediadoma.com\/es\/wp-json\/wp\/v2\/comments?post=229184"}],"version-history":[{"count":0,"href":"https:\/\/wordpress.mediadoma.com\/es\/wp-json\/wp\/v2\/posts\/229184\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/wordpress.mediadoma.com\/es\/wp-json\/wp\/v2\/media\/220946"}],"wp:attachment":[{"href":"https:\/\/wordpress.mediadoma.com\/es\/wp-json\/wp\/v2\/media?parent=229184"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/wordpress.mediadoma.com\/es\/wp-json\/wp\/v2\/categories?post=229184"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/wordpress.mediadoma.com\/es\/wp-json\/wp\/v2\/tags?post=229184"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}