Buggy CakePHP Code: Los 6 errores más comunes que cometen los desarrolladores de CakePHP

Publicado: 2022-03-11

CakePHP es un marco PHP increíble, ¡pero tiene una curva de aprendizaje empinada! Se requiere una buena cantidad de investigación y capacitación para convertirse en un experto.

He tenido la suerte de usar CakePHP durante más de 7 años, y en ese tiempo he tenido el honor de trabajar con muchos miembros de la comunidad CakePHP.

En este tutorial de CakePHP me gustaría describir algunas malas prácticas que he visto a lo largo de los años y proponer el enfoque correcto para evitar estos errores. Esto no quiere decir que mi código sea perfecto, pero como programadores siempre estamos aprendiendo, por lo que es importante seguir las mejores prácticas y ajustar a medida que aprende.

El contenido de este artículo está inspirado en una publicación de CakeCoded. Si desea obtener más información sobre CakePHP, visite nuestra sección de aprendizaje aquí.

¡Este tutorial de CakePHP para principiantes te ayudará a evitar freír tu código CakePHP con errores y equivocaciones!

Error común #1: no seguir las convenciones de codificación de CakePHP

Las convenciones de codificación de CakePHP se pueden ver aquí. Destacaré algunas cosas que a menudo noto cuando veo el código de otros programadores.

Estructuras de Control. Muy a menudo ves que los programadores se equivocan y, en algunos casos, traen prácticas de otros lenguajes de codificación. CakePHP espera la siguiente sintaxis:

 if ((expr_1) || (expr_2)) { // action_1; } elseif (!(expr_3) && (expr_4)) { // action_2; } else { // default_action; }

Debe haber 1 (un) espacio antes del primer paréntesis y 1 (un) espacio entre el último paréntesis y el paréntesis de apertura. Entonces esto significa que lo siguiente es incorrecto:

 if($this->request->data){ }

Tenga en cuenta el espacio entre if y ( , y between ) y {

Utilice siempre corchetes en las estructuras de control, incluso si no son necesarios. Aumentan la legibilidad del código y le dan menos errores lógicos.

Entonces, por ejemplo, lo siguiente es incorrecto:

 if ($foo) $bar = true

Esto debería tener el siguiente formato:

 if ($foo) { $bar = true }

Finalmente, observe dónde coloca los soportes. Los corchetes de apertura no deberían comenzar una nueva línea. Y asegúrese de que todos sus corchetes estén alineados para que cada nuevo corchete esté alineado con el corchete de cierre.

Aquí hay algunos ejemplos incorrectos:

 if ($foo) { $bar = true; }

Esto es incorrecto, el paréntesis de apertura debe estar en la primera línea:

 if ($foo) { $bar = true; if ($action) { $to = false; } }

La sangría debe alinearse correctamente.

A menudo escucho a los programadores decir: "Pero estoy demasiado ocupado para hacer que el código sea ordenado...". Mi respuesta es: "Confía en mí, el código ordenado resistirá la prueba del tiempo". Escribir código CakePHP que no sea legible será una pesadilla si necesita hacer un cambio en unos meses.

Error común n.º 2: uso inadecuado de comportamientos contenibles y niveles recursivos en ORM

Recientemente tuve la suerte de tener una conversación informal con un desarrollador de base de datos de Facebook. Empezamos a hablar de CakePHP y me dijo: “Oh, eso usa ORM, ¿no? Eso puede dar miedo”. Le pregunté qué quería decir y comentó que con el mapeo relacional de objetos (ORM) es fácil que las consultas SQL se vuelvan innecesariamente grandes.

Tiene razón en cierto modo. Parte de la magia de CakePHP está en su uso de ORM y la forma en que agrupa diferentes relaciones de tablas de bases de datos. Por defecto, CakePHP selecciona automáticamente cualquier dato relacionado 'Pertenece a', 'Tiene uno' y 'Tiene muchos', y esto puede llevar a consultas SQL muy grandes. Es posible que estas consultas no sean una preocupación cuando desarrolla inicialmente una aplicación, pero después de seis meses de recopilar datos en vivo, es posible que la aplicación se vuelva muy lenta y, en algunos casos, se bloquee si las consultas no están optimizadas.

Me fijo en dos cosas cuando audito un sitio web existente. En primer lugar, ¿se ha cambiado el nivel recursivo predeterminado? Por defecto, CakePHP establece el nivel recursivo en 1, que en mi opinión es demasiado alto. Siempre lo configuro en -1 y luego uso el comportamiento contenedor para obtener cualquier modelo relacionado.

Eso lleva a la segunda cosa que busco: ¿se ha utilizado el comportamiento Containable? A menudo tengo nuevos clientes que me dicen que CakePHP es lento. ¡La razón casi siempre es porque Containable no se ha utilizado! Un buen programador de CakePHP optimizará sus consultas SQL independientemente de cuánta "auto-magia" se haga detrás de escena.

El comportamiento contenible no se agregó hasta CakePHP 1.2, pero ¿ha marcado la diferencia? Asegúrese de usar lo más contenido posible, ya que es una forma muy efectiva de optimizar su SQL. Para obtener más información sobre cómo implementar y utilizar el comportamiento de Containable, haga clic aquí.

Error común n.º 3: mantener la lógica empresarial en controladores en lugar de modelos

Un buen código CakePHP tendrá la lógica en los archivos del modelo. Esto toma un poco de tiempo para acostumbrarse, pero una vez que se domina, ¡no hay vuelta atrás! Se debe usar un archivo de controlador para lo que está destinado en el patrón MVC: ¡controlar! Por lo tanto, use su archivo de controlador para manejar las acciones del usuario, mientras deja que la lógica comercial vaya en el archivo modelo.

Un buen ejemplo de esto sería un CRUD simple: ¡una acción cotidiana! Tomemos como ejemplo la función de agregar publicaciones de un tutorial de blog. La función de adición predeterminada es la siguiente:

 public function add() { if ($this->request->is('post')) { $this->Post->create(); if ($this->Post->save($this->request->data)) { $this->Session->setFlash(__('Your post has been saved.')); return $this->redirect(array('action' => 'index')); } $this->Session->setFlash(__('Unable to add your post.')); } }

Esta acción del controlador está bien para una adición simple, pero ¿qué pasaría si quisiera hacer cosas como enviar un correo electrónico al administrador cuando se agrega una publicación o actualizar otra asociación modelo cuando se agrega una publicación? Esta es una lógica adicional, pero esta lógica no debería entrar en nuestro archivo de controlador.

En su lugar, escribiríamos una función para esto en nuestro modelo Post.php . Tal vez algo como esto:

 public function addPost($data = array(), $emailAdmin = true) { $this->create(); $this->save($data); // update any other tables // send the email to the admin user if ($emailAdmin) { } // if all is successful return true; }

Esto daría como resultado un pequeño cambio en la acción del controlador de la siguiente manera:

 public function add() { if ($this->request->is('post')) { if ($this->Post->addPost($this->request->data)) { $this->Session->setFlash(__('Your post has been saved.')); return $this->redirect(array('action' => 'index')); } $this->Session->setFlash(__('Unable to add your post.')); } }

Como puede ver, la nueva acción es en realidad una línea menos, porque $this->Post->create() se ha movido al archivo modelo.

Este es un ejemplo perfecto y cotidiano de dónde mover la lógica al archivo del modelo es una buena idea, ¡y ciertamente lo convierte en una base de código mucho más limpia!

Error común n.° 4: agregar demasiada complejidad al código, en lugar de regresar con frecuencia y antes de tiempo

Este es siempre un debate en curso, pero regresar a menudo y regresar temprano ciertamente hace que el código se vea mucho más limpio. Esto se aplica a los métodos del modelo más que a cualquier otra cosa.

Pero, ¿a qué me refiero exactamente? Bueno, echemos un vistazo al método que agregamos en el tutorial de CakePHP anterior:

 public function addPost($data = array(), $emailAdmin = true) { $this->create(); $this->save($data); // update any other tables // send the email to the admin user if ($emailAdmin) { } // if all is successful return true; }

Regresar a menudo y regresar temprano significa que a medida que ejecutamos nuestra función, verificamos para asegurarnos de que todo esté bien de forma regular. Si no es así, devolvemos falso o devolvemos un error de CakePHP.

Podría ser más fácil mostrar esto con un ejemplo. Hay dos formas de escribir la función anterior:

 public function addPost($data = array(), $emailAdmin = true) { if ($data) { $this->create(); $result = $this->save($data); if ($result) { // update any other tables // send the email to the admin user if ($emailAdmin) { // send the admin email } } else { // problem saving the data return false; } // if all is successful return true; } else { // no data submitted return false; } }

¿Ves cómo el código se vuelve rápidamente ilegible? Hay if s y else s por todas partes, y la función se convierte rápidamente en una gran sangría. No me malinterpreten, me encanta la sangría limpia, pero mire cómo se ve la función si se escribe con el retorno a menudo, el principio de retorno temprano.

 public function addPost($data = array(), $emailAdmin = true) { if (!$data) { // no data submitted return false; } $this->create(); $result = $this->save($data); if (!$result) { // problem saving the data return false; } // update any other tables // send the email to the admin user if ($emailAdmin) { // send the admin email } // if all is successful return true; }

Inmediatamente, en este pequeño ejemplo, puede ver que el código solo tiene una sola sangría y es mucho más legible. La lógica en realidad tiene más sentido: deje que la lógica se ejecute línea por línea y, si hay algún problema en el camino, devuelva el error y no continúe con la siguiente línea.

Esto permite que un programador de CakePHP escriba de la misma manera que nosotros leemos: leyendo el código de izquierda a derecha, de arriba a abajo, en lugar de en diferentes bloques, ¡lo que puede volverse confuso rápidamente!

Error común #5: No usar el principio SECO

DRY significa Don't Repeat Yourself, y es una filosofía que debe seguirse al codificar en CakePHP. ¡Con el código orientado a objetos, no hay excusa para repetir el mismo bloque de código dos veces!

Aquí hay algunos consejos de CakePHP para asegurarse de que no se repita:

  • Como se mencionó anteriormente, trate de poner la lógica en los archivos modelo para que pueda compartir la lógica.

  • En sus archivos de vista, si está repitiendo vistas, cree el código de vista como un Elemento, o incluso como un asistente personalizado.

  • Configure algunos ajustes de configuración: el archivo app/Config/bootstrap.php es un excelente lugar para esto. Esto ayuda a asegurarse de que no esté codificando cosas como el nombre de la aplicación y la dirección de correo electrónico principal. Lo último que desea hacer es revisar cientos de archivos solo porque el cliente solicitó actualizar una dirección de correo electrónico en una aplicación.

  • Siempre pregúntese: "Si estoy repitiendo el código, ¿hay una mejor manera de escribir este código y estoy colocando este código en el lugar correcto?" Lo más probable es que, si necesita repetir el código, podría escribirse mejor.

Error común n.º 6: no comentar el código

El último punto que haré es con respecto a los comentarios. En primer lugar, el bloqueo de documentos. Un bloque de documentos es cuando documentas un método o una acción. Solo toma un minuto registrar un poco sobre lo que está haciendo una función, pero hace una gran diferencia en términos de legibilidad del código.

Los bloques de documentos de CakePHP deben ir contra el margen izquierdo de la página. Entonces, un ejemplo simple usando el código de arriba.

 /** * Adds & saves a post as well as emails the admin to let them know the post has been added. * Also performs some saving to another table * * @param array $data The post data * @param bool $emailAdmin If set to true, will email the website admin * @return bool Returns true if successful */ public function addPost($data = array(), $emailAdmin = true) {

Como verá, no toma mucho tiempo escribir un bloque de documentos, pero hace una gran diferencia en términos de longevidad del código. En última instancia, significa que el código puede vivir más allá de usted como desarrollador.

Del mismo modo con los comentarios en línea. ¡No tenga miedo de explicar qué está haciendo su código y por qué! A largo plazo, hace que sea mucho más fácil comprender su código, ¡especialmente si otro desarrollador lo está mirando!

Envolver

CakePHP es un marco extenso y con todas las funciones. Dado que sigue la convención sobre la configuración, CakePHP es más estricto que otros marcos basados ​​en PHP, en el sentido de que un usuario está "obligado" a seguir una determinada forma de diseñar el código. Esto puede ser controvertido, pero en mi experiencia conduce a una base de código que es más coherente, legible y comprensible: en lugar de dejar que un desarrollador "elija" cómo debe escribirse el código, un equipo de desarrollo escribirá un código coherente siguiendo las convenciones de Cake. .

Siguiendo este tutorial de CakePHP y asegurándose de que su código esté bien escrito, las aplicaciones pueden resistir el paso del tiempo. El código siempre debe escribirse para el mañana, de modo que si otro desarrollador está mirando un bloque de código en particular años más tarde, comprenderá el código y se ajustará a los estándares esperados. CakePHP no es diferente y esperamos que esta guía ayude a corregir algunos malos hábitos.