Este foro ya no está activo, así que no puedes publicar nuevas preguntas ni responder a las preguntas existentes.

¿Como subir un archivo SQL a symfony?

3 de julio de 2016

Hola cordial saludo a todos, quisiera que por favor me den una idea sobre lo siguiente: deseo subir desde mi proyecto en Symfony 2.7, un archivo SQL con unos registros que necesita el software agradezco que me den una idea de como podría hacerlo. Gracias!


Respuestas

#1

He logrado mi objetivo este es mi código y funciona perfectamente:

/**
     * @Route("/importar", name="importar")
     * @Template("SeguridadBundle:Default:index.html.twig")
     */
    public function importarAction(Request $request)
    {
 
        /**
         * Creo un formulario para Seleccionar el archivo SQL
         */
        $defaultData = array('message' => 'Type your message here');
        $form = $this->createFormBuilder($defaultData)
            ->add('archivo', 'file', array('label' => 'Seleccione el Archivo SQL: '))
            ->getForm();
 
        $form->handleRequest($request);
 
        if ($form->isSubmitted() && $form->isValid()) {
 
            /**
             * Obtengo la ruta del Archivo y lo Muevo hasta
             * mi propio directorio dentro de la Aplicacion symfony
             */
            $file= $form->get('archivo')->getData();
            $nombre='SQLimportado'.date("dmYHis", time()).'.sql';
            $cvDir = $this->container->getparameter('kernel.root_dir').'\Resources\importados\\';
            $file->move($cvDir,$nombre);
 
            /**
             * Busco el archivo utilizando los datos anteriores
             * como la ruta y el nombre del archivo
             */
            $finder = new Finder();
            $finder->files()->in($cvDir);
            $finder->name($nombre);
 
            foreach ($finder as $file) {
                /**
                 * Ejecuo el SQL
                 */
                $contenido = $file->getContents();
                $em = $this->getDoctrine()->getEntityManager();
                $db = $em->getConnection();
                $resultado=$db->prepare($contenido);
                $resultado->execute();
                var_dump($resultado->errorInfo());
 
            }
        }
 
        return array(
            'form'   => $form->createView(),
        );
 
    }

Ahora lo que quisiera saber es, ¿cómo puedo saber si el SQL se ha ejecutado correctamente y cuando no?

@YulianDavid94

3 julio 2016, 6:03
#2

Me respondo nuevamente: he completado el código para validar si el SQL se ejecuta en su totalidad o no, aquí el código completo.

Al final he conseguido un resultado: lo que hice fue ejecutar el archivo SQL mediante mysqli, no con el Manager de Doctrine.

/**
     * @Route("/importar", name="importar")
     * @Template("SeguridadBundle:Default:index.html.twig")
     */
    public function importarAction(Request $request)
    {
 
        /**
         * Creo un formulario para Seleccionar el archivo SQL
         */
        $defaultData = array('message' => 'Type your message here');
        $form = $this->createFormBuilder($defaultData)
            ->add('archivo', 'file', array('label' => 'Seleccione el Archivo SQL: '))
            ->getForm();
 
        $form->handleRequest($request);
 
        if ($form->isSubmitted() && $form->isValid()) {
 
            /**
             * Obtengo la ruta del Archivo y lo Muevo hasta
             * mi propio directorio dentro de la Aplicacion symfony
             */
            $file= $form->get('archivo')->getData();
            $nombre='SQLimportado'.date("dmYHis", time()).'.sql';
            $cvDir = $this->container->getparameter('kernel.root_dir').'\Resources\importados\\';
            $file->move($cvDir,$nombre);
 
            /**
             * Busco el archivo utilizando los datos anteriores
             * como la ruta y el nombre del archivo
             */
            $finder = new Finder();
            $finder->files()->in($cvDir);
            $finder->name($nombre);
 
            foreach ($finder as $file) {
                /**
                 * Seobtiene el contenido del SQL
                 * y se Crea la conexion a MySQL
                 */
                $contenido = $file->getContents();
                $em = $this->getDoctrine()->getEntityManager();
                $parametros = $em->getConnection()->getParams();
 
                /**
                 * Creo un nuevo parametro de Mysqli
                 */
                $mysqli = new \mysqli(
                    $parametros['host'],
                    $parametros['user'],
                    $parametros['password'],
                    $parametros['dbname']);
 
                /**
                 * Ejecutor el archivo SQL
                 * mediante la opcion de, multiple query
                 * y valido si existen errores durante su ejecucion
                 */
                if ($mysqli->multi_query($contenido)) {
                    do {
 
                        if (!$mysqli->more_results()) {
                            break;
                        }
                        if (!$mysqli->next_result()) {
                            /**
                             * si hay error de algun tipo Se Mostrara el mensaje de ERROR
                             */
                            return $this->render('SeguridadBundle:Default:respuesta.html.twig', array(
                                'resultado' => 'Seha producido un error durante la ejecución del SQL!',
                            ));
                            break;
                        }
                    } while (true);
                    /**
                     * si todo esta bien Se muestra el MSG de CORRECTO
                     */
                    return $this->render('SeguridadBundle:Default:respuesta.html.twig', array(
                        'resultado' => 'La importación de ha ejecutado correctamente!',
                    ));
                }
                else {
                    /**
                     * si hay error de algun tipo Se Mostrara el mensaje de ERROR
                     */
                    return $this->render('SeguridadBundle:Default:respuesta.html.twig', array(
                        'resultado' => 'Seha producido un error durante la ejecución del SQL!',
                        'error'=>$mysqli->errno
                    ));
 
                }
            }
        }
 
        return array(
            'form'   => $form->createView(),
        );
 
    }

@YulianDavid94

4 julio 2016, 0:32
#3

Aunque ya supongo que serás consciente, esta funcionalidad es potencialmente muy peligrosa. Estás ejecutando un archivo SQL directamente contra la base de datos, así que algún usuario malicioso podría incluir la instrucción DROP DATABASE nombre_base_de_datos; y borrarte toda la base de datos de producción.

Como solución alternativa, podrías hacer lo siguiente:

  1. Crear un usuario especial en esa base de datos (llamado por ejemplo importador) y quitarle todos los permisos salvo los imprescindibles para importar datos mediante el archivo SQL.
  2. Usar el componente Process para ejecutar el comando mysql -u importador -p nombre_base_datos < archivo.sql
  3. Obtener el código de retorno devuelto por el proceso para saber si ha funcionado o ha habido algún error.

Los puntos 2 y 3 no son más seguros que la solución que propones, pero me parecen una forma más rápida de hacer lo mismo que haces mediante las funciones mysqli.

@javiereguiluz

4 julio 2016, 8:24