2009-04-11 27 views
8

Estoy tratando de usar SQLAlchemy para implementar un modelo básico de grupos de usuarios donde los usuarios pueden tener múltiples grupos y grupos pueden tener múltiples usuarios.SQLAlchemy deleción huérfana de muchos a muchos

Cuando un grupo se vacía, quiero que se elimine el grupo (junto con otras cosas asociadas con el grupo. Afortunadamente, la cascada de SQLAlchemy funciona bien con estas situaciones más simples).

El problema es que cascade = 'all, delete-orphan' no hace exactamente lo que quiero; en lugar de eliminar el grupo cuando el grupo se vacía, elimina el grupo cuando cualquier miembro deja el grupo.

Agregar desencadenadores a la base de datos funciona bien para eliminar un grupo cuando se vacía, excepto que los desencadenadores parecen omitir el procesamiento en cascada de SQLAlchemy para que las cosas asociadas con el grupo no se eliminen.

¿Cuál es la mejor manera de eliminar un grupo cuando todos sus miembros se van y tienen esta cascada de eliminación a las entidades relacionadas.

Entiendo que podría hacer esto manualmente buscando en cada lugar de mi código donde un usuario puede abandonar un grupo y luego hacer lo mismo que el desencadenante; sin embargo, me temo que omitiría lugares en el código (y soy flojo).

+0

Creo que puede ser un poco complicado responder a esta pregunta sin más detalles sobre tu código (cómo has configurado la relación de muchos a muchos, dónde has puesto el huérfano de eliminación, etc.), más o menos lo es el esquema, etc. –

+0

Probé el delete-huérfano en el backref y la relación normal(). La relación es básicamente mapper (Usuario, usuarios, propiedades = {'groups': relation = relation (Group, secondary = users_groups, backref = backref ('users'))}) –

Respuesta

3

La forma en que generalmente he manejado esto es tener una función en su usuario o grupo llamada leave_group. Cuando desea que un usuario abandone un grupo, llama a esa función y puede agregar los efectos secundarios que desee allí. A largo plazo, esto hace que sea más fácil agregar más y más efectos secundarios. (Por ejemplo, cuando quiere verificar que alguien puede abandonar un grupo).

3

Creo que quieres cascade='save, update, merge, expunge, refresh, delete-orphan'. Esto evitará la cascada de "eliminar" (que obtienes de "todos") pero mantendrás el "eliminar-huérfano", que es lo que estás buscando, creo (eliminar cuando no haya más padres).

+1

En SA 0.6: 'The 'delete- la opción huérfana en cascada requiere 'eliminar' – ThiefMaster

0

¿Podría publicar una muestra de su tabla y configurar el asignador? Puede ser más fácil detectar lo que está sucediendo.

Sin ver el código es difícil de decir, pero tal vez hay algún problema con la dirección de la relación?

2

Tuve el mismo problema hace 3 meses, tengo una relación Publicar/Etiquetas y quería eliminar las etiquetas no utilizadas. Le pregunté en IRC y el autor de SA me dijo que las cascadas en las relaciones de muchos a muchos no son compatibles, lo que tiene sentido, ya que no hay un "padre" en muchos-a-muchos.

Pero extender SA es fácil, probablemente pueda usar un AttributeExtension para verificar si el grupo se vació cuando se elimina de un Usuario y eliminarlo de allí.

Cuestiones relacionadas