[SOLUCIONADO] Tablas múltiples sobre un solo "registro atómico"

Hola, quisiera pedirles consejo sobre como atacar la situación que planteo más abajo y ante todo, les pido disculpas, ya que al no conocer todas las opciones y posibilidades de la herramienta, consumo demasiado tiempo intentando pensar la mejor forma de solucionar problemas puntuales, y finalmente cuando lo hago, nunca tengo claro si hubiera sido la mejor alternativa:

Situación

  1. tabla_padre: id, idhijo1, idhijo2, otrodato
  2. tabla_hijo1: id, fechaini, fechafin, otrodato1
  3. tabla_hijo2: id, fechaini, fechafin, otrodato2
    En realidad, una vez completo, representan un único registro atómico.
    Es decir, un registro de la tabla_padre existirá si y solo si, existe uno y solo un registro asociado en tabla_hijo1, y tabla_hijo2.

Alternativa 1
La primer intención, que se me ocurrió, era hacer 2 pantallas, la primera de selección, y la segunda de edición, con un ci y 2 nuevas pantallas, una para editar los datos de tabla_hijo1, y otro para tabla_hijo2. Para esto, utilzaría una relación y setearía min y max filas en las tablas de relación en 1 para todos los campos, y manejaría cualquier cambio en la fuente de datos a través de la relación.
Esta no es la opción que me gustaría tomar, ya que al ser solapas separadas, el usuario pierde la noción de atomicidad implícita.

Alternativa 2
Otra idea, sería tener un cuadro con todos los datos, y en la misma pantalla o en otra de edición, 3 formularios, uno debajo del otro, que se acepten, eliminen o modifiquen en conjunto con eventos dentro del ci controlador.
En este punto, las consultas puntuales son las siguientes:
1) puedo incluir más de un formulario en un ci?
2) debería incluir cada tabla por separado, o mantengo la relación de las tablas?
3) Intuitivamente, me parece que podría utilizar la relación, y 3 formularios, uno arriba del otro… y aplicar todo si fueran distintas solapas… como si fuera la alternativa 1), es decir como si estuvieran en solapas separadas? en este caso definiría en cada formulario un evento modificacion, pero se dispara en que momento? cada vez que edito un ef? porque en ese evento debería hacer el set, y luego en el evento aplicar del ci controlador sincronizar.

Alternativa 3
Un solo cuadro y un solo formulario
En este caso,
1) como podría hacer el guardado de los datos, la recuperación de los mismos para edición y la eliminación atómica?
2) sería mejor seguir utilizando la relación, o 3 datos_tabla por separado y atacarlos a cada uno por separado ante la selección, eliminación, etc en cada evento particular?

Desde ya, MIL GRACIAS!

Si, solo tenes que agregarlos como dependencias distintas en el CI y asignarlos a la pantalla correcta.

2) debería incluir cada tabla por separado, o mantengo la relación de las tablas?

Podes hacerlo de cualquiera de las 2 formas, la que te quede mas comoda… toma en cuenta que la relacion te maneja la transaccion automaticamente… si lo haces con datos_tabla separados vas a tener que hacer un manejo de transacciones explicito.

3) Intuitivamente, me parece que podría utilizar la relación, y 3 formularios, uno arriba del otro... y aplicar todo si fueran distintas solapas... como si fuera la alternativa 1), es decir como si estuvieran en solapas separadas? en este caso definiría en cada formulario un evento [u]modificacion[/u], pero se dispara en que momento? cada vez que edito un ef? porque en ese evento debería hacer el [u]set[/u], y luego en el evento [u]aplicar [/u]del ci controlador [u]sincronizar[/u].

Lo que deberias hacer es definir los eventos de modificacion de cada formulario como implicitos (imagen 1). Eso significa que cada vez que se haga un envio al servidor los datos de dicho formulario viajaran hacia el mismo. Lo que podrias hacer luego es definir un par de eventos a nivel de CI, digamos un ‘Guardar’ y ‘Cancelar’ que realicen la interaccion con el servidor, esos serian los eventos que dispararian el envio de datos (imagen 2). Del lado del servidor tendrias los metodos para escuchar las modificaciones de los formularios y la sincronizacion la dispararias desde el metodo que captura el ‘Guardar’. De esta forma la operacion te quedaria ‘atomica’, aunque en realidad sean 3 datos_tabla distintos.

Te comento que a gusto mio en este tipo de casos queda bueno tener un cuadro de seleccion en una primer pantalla y los formularios para la edicion en otra, la navegacion entre las pantallas la vas manejando vos explicitamente en los eventos de seleccion del cuadro y en los eventos de procesamiento (Guardar/Eliminar/Cancelar). Para ello seteas que la navegacion del Ci queda a cargo de la subclase y usas para los cambios de pantalla el metodo $this->set_pantalla(‘id_pantalla’);

Saludos
Richard


Seguí esa línea, pero hay algo en lo que fallo.
Tengo configurada la relación de forma tal que acepte un solo registro de cada uno.
Son 2 pantallas, una de selección y la otra de edición (imgOPERACION).
Cuando hago un alta (imgALTA), entonces, me tira un error que indica que los datos de la tabla hija no están cargados. Es decir, no toma los datos ingresados en ese formulario.
En realidad, los formularios nunca procesan el evt__xxx__modificacion, declarado implícito en ellos, solo el formulario principal o de la tabla padre.
Te adjunto el código del ci, por si es de utilidad.


Te hago una consulta, tanto los eventos implicitos de los formularios como el evento aplicar del CI tienen el tilde ‘Maneja Datos’ activado?. Si eso es asi te pediria que me subieras el archivo de log ya que el codigo pareciera estar correcto.

Saludos
Richard

Si, estaban tildados (no tengo a mano el ambiente de desarrollo). Pero me fijé especificamente en su momento.
El tema es que no se disparan los eventos modificar, capaz hay que setear los formularios como en cascada? o dentro de un ci aparte?
En cuanto pueda te adjunto el log…

Si, confirmado, en los 3 formularios está definido un único evento, modificacion (en los 3 se llama igual), como implicito y manteniendo datos (de hecho, quise sacar ese tilde para volver a generarlo, pero no me dejó… tiene que estar tildado).
Te adjunto el log con la traza del error.
Hay que tener en cuenta que docentes_cargos (… id_cargo… id_vinculacion) depende de que cargos y vinculaciones hayan sido dadas de alta primero. Sin embargo, por una cuestión de lógica visual del usuario, es el primer formulario.


Te adjunto la configuración de la relación por si el problema anda por ahi.


Si este es el caso tienes la relacion definida al reves… lo que buscas es un grafo similar a una V… con cargos y vinculaciones como padres y docentes_cargos como hijo de ambas tablas.

Mas alla de eso me intriga el hecho de que no dispare los eventos de modificacion de los formularios, podrias enviarme una captura de pantalla de la solapa eventos del CI que controla toda la operacion? tambien adjuntame capturas de las solapas de eventos de los 3 formularios por favor.

Saludos

Te los paso, pero capaz es un problema de la relación… pese a haber 2 padres, podría utilizar el mismo esquema?


OK, analicemos un poco el tema de la relacion entonces, la idea es que te quede algo como lo que se ve en la imagen, al menos para que no salten las FK.

Una vez tengas la relacion asi, vas a tener que realizar algunos cambios igualmente, ya sean visuales o a nivel de CI. Te explico por que.

1.- Para poder dar de alta un registro en docentes_cargos ambos padres deben tener un registro creado que ademas automaticamente posicionara el cursor en dicho registro. Osea se necesita un cursor en cada uno de los padres.

2.- Los eventos de modificacion se lanzan en el orden en que se encuentran las dependencias en la pantalla, osea siguiendo el orden visual.

Segun veo de las imagenes que me enviaste, el formulario de docentes_cargo (si mal no calculo) es el primero visualmente, por lo tanto se tratara de agregar primeramente el registro en la tabla hija… lo cual va a explotar (menos mal que no hay yankees sino ya tendria al FBI aca)… por lo tanto tendriamos que tratar de serializar los eventos de modificacion para que respeten el orden de la relacion(1) … o sino en su defecto hacer que la relacion sea independiente del orden de los eventos(2).

1.- Necesariamente tendrias que completar los formularios correspondientes a las tablas padres antes… osea cambio de posicion en pantalla.

2.- Podrias trabajar las modificaciones en variables de clase que perduren en sesion (s__nombre_variable) y al momento de aplicar los cambios ordenar explicitamente la forma en que se crean los registros en las tablas, lo malo de esto es que tanto el datos_relacion como datos_tabla quedan relegados a ser un mero generador de SQL, tanto para lectura como para escritura.

Otro tema (diria Santos)… realmente que los eventos se corten asi sin ningun motivo aparente me llama la atencion… asi que vamos a la ultima opcion… si se puede y no te pone en un compromiso, podrias enviarme el proyecto comprimido a mi dir de mail? asi puedo atacarlo localmente y trazearlo para ver porque falla.

Saludos


Uhmmm… pasarte el proyecto va a ser medio difícil, no depende de mi, sino que necesitaría autorización (más allá de saber lo útil que sería!!!).
Puedo enviarte todas las capturas de pantallas de la operación en particular, y la definición interna de la base de datos que se corresponde con esto.

Igual, pasando todo en limpio:

  1. Tendría que generar si o si formularios en distintos TABs.
  2. Cambiar la relación (darla vuelta).
  3. Ordenar los eventos en el ci.

Sería eso, no?

No problemo… por eso el pedido era condicionado a tus posibilidades, no te preocupes.

Puedo enviarte todas las capturas de pantallas de la operación en particular, y la definición interna de la base de datos que se corresponde con esto.

Creo que en las pantallas ya no hay mucho mas que mirar… como bien dijiste vos antes tenes todo lo que haria falta. Aunque la definicion de la bd estaria interesante para ver si podemos sacar algo extra.

Igual, pasando todo en limpio: 1) Tendría que generar si o si formularios en distintos TABs.
No necesariamente, podes ponerlos todos en el mismo tab... pero es necesario que el orden de carga de datos sea otro.
2) Cambiar la relación (darla vuelta).
Esto depende pura y exclusivamente de como sea la ddl de esas tablas en bd. Sin tenerlas a mano solo me guio por lo que me contas y pareciera estar al reves. Por cierto en el post anterior no te habia subido la imagen, ahi te la agregue.. disculpa.
3) Ordenar los eventos en el ci.
Esto depende de como elijas hacer el punto 1.

Me inclino por seguir con el mismo orden visual, en una sola pantalla, un formulario debajo de otro.
Cambié el orden de los eventos en el CI y redefiní la relación. En 2 pasos consecutivos. Primero, me dió el mismo error. Cuando agregué el cambio de la relación, que quedó como una V, me tiró el error que te adjunto.
Probablemente chequee con el diseñador de la BDD la necesidad de tener separadas la tablas, y si son realmente atómicos (sin ninguna excepción que pudiera aparecer a futuro), entonces probablemente corte por lo sano y arme una sola tabla. Por suerte, estamos aún a tiempo de hacer este tipo de cambios.
Más allá de eso, te adjunto también la definición de la base de datos (pero para mi, originalmente, estaba bien definida la relación).
Mil gracias…


El error que te esta saltando es porque se esta haciendo el set de la tabla hija antes de alguno de los padres… algo que me comento seba y que yo no me percate es que no necesitas esperar hasta el evt__aplicar para hacer la llamada al metodo set de cada datos_tabla… lo podes hacer en el metodo post_eventos mientras coloques las llamadas en el orden correcto no deberias tener drama.

Probablemente chequee con el diseñador de la BDD la necesidad de tener separadas la tablas, y si son realmente atómicos (sin ninguna excepción que pudiera aparecer a futuro), entonces probablemente corte por lo sano y arme una sola tabla. Por suerte, estamos aún a tiempo de hacer este tipo de cambios.

La verdad el diseño esta bastante raro (quizas tenga sus razones) la tabla de docentes_cargos pareciera una relacion 1->N, de las otras 2 tablas restantes involucradas la unica que me imagino sola podria ser la de cargos (incluso hasta se podria hacer un ABM particular para ella)… la tabla de vinculacion creo que no tiene razon para existir… esa info bien podria estar dentro de docentes_cargos creo yo. Con respecto a la tabla de cargos… si no existe un ABM separado para darlos de alta como si fueran una ‘entidad’ probablemente tambien deberia ser absorvida por docentes_cargos.

Más allá de eso, te adjunto también la definición de la base de datos (pero para mi, originalmente, estaba bien definida la relación).
La definicion me vino barbaro gracias :). Lo cierto es que pareciera tener mas sentido para el datos_relacion cargar un docente_cargo.... que una combinacion (cargo, vinculacion). El problema es que las FK estan invertidas en la bd y el datos_relacion debe reflejar ese sentido, por lo tanto cargo y vinculacion deben ser los padres. Si colocan las FK de manera distinta entonces como vos bien decis la definicion original del datos_relacion estaria bien. De todas formas eso ya es algo que tenes que charlar con el Diseñador del modelo.

Saludos

En realidad, mi confusión surgia del modelo en si mismo… se redefinió completamente!! asi que este problema, dejó de ser tal.
MIL Gracias igual por la respuesta.

No le pongo solucionado a este tema ya que pretendia sugerir que el mismo fuese eliminado porque no aportará nada a la comunidad en general.
Muchos saludos y MIL GRACIAS NUEVAMENTE!!!

Martin,
me alegro que se haya solucionado, por lo del tema no te preocupes… todo siempre aporta algo… asi que lo marco como resuelto.

Saludos