Pregunta

Lo que estoy tratando de hacer es la siguiente:

En cualquier momento el usuario puede tener 1 perfil activo. Este perfil activo debe ser autorizado por un administrador para asegurarse de que cumple con las normas y reglamentos del sitio. Cuando un usuario edita su perfil su perfil público no se ve afectada hasta que el administrador se despide sus cambios. Si hacen una edición mientras que su perfil está en revisión, sus ediciones se aplican al perfil sobresaliente para su revisión y se inserta en la parte posterior de la cola.

Mis modelos tienen el siguiente aspecto:

class Profile < AR:B
    belongs_to :user
end

class User < AR:B
    has_many :profiles do
        def active
            ...
        end
        def latest
        end
    end
    def profile
        self.profiles.active
    end
end

Hay un pequeño giro ... el usuario no debe ser capaz de modificar el perfil directamente, como la colección de perfiles no está expuesto. En su lugar, editar su usuario y los campos de perfil se muestran allí.

¿Cuál es la mejor manera de manejar esto? Actualmente estoy usando:

accepts_nested_attributes_for :profiles

En el usuario, pero que parece bastante hacky. Lo ideal sería que la mayor parte de esta lógica vivirían en el modelo, pero la otra cosa que estoy coqueteando con es el uso de un presentador.

Cualquier idea sería muy apreciada, que me haga saber si necesita más información como un comentario y voy a actualizar este post adecuadamente.

¿Fue útil?

Solución

Tal vez debería intentar tener dos relaciones de usuario perfil. Una de ellas es la que ellos pueden editar a través de su interfaz de usuario, y el otro es el que es aprobado por el administrador.

Se podría trabajar algo como:

class User < AB:B

has_one :profile #the user-editable one one
has_one :active_profile, :class_name=>"profile" #the one shown

end

Cada cambios en el perfil del usuario a través del formulario a continuación se muestran para el administrador (usando y observador o tal vez sólo y "after_save" filtro). Cuando se APRUEBA ella, los cambios se vierten a la active_profile uno, y se muestran en alguna parte.

De esta manera, se puede tener una interfaz de forma limpia y siempre que editar de nuevo, lo consideran el último perfil (pero no aprobado). También puede ordenar la cola utilizando la columna updated_at para ganar los "sus ediciones se aplican al perfil sobresaliente para su revisión y se inserta en la parte posterior de la cola" funcionalidad.

Otros consejos

Me ir sobre esto haciendo que el modelo de usuario tiene una relación con dos perfiles como se sugirió anteriormente también. Una "Aprobado" el perfil, y el otro para la edición que entra en su cola de administración.

Sin embargo, con el fin de manejar las transiciones entre los "pendientes" y "perfiles aprobados" perfiles Yo sugeriría posiblemente la adición de una máquina de estados para manejar las transiciones. La gema AASM ha sido bueno para mí en un proyecto reciente. ( http://github.com/rubyist/aasm/tree/master ), y creo que Edge Rails tiene derecho justo al horno de Estado en Machinage también. ( http://github.com/rails/rails/commit/aad5a30bf25d8a3167afd685fc91c99f4f09cc57 )

Su modelo podría ser algo como esto:

class User < AR:B

has_one :active_profile 
has_one :pending_profile

include ActiveRecord:: StateMachine

state_machine do
   state :approved
   state :pending
   state :rejected

   event :update_profile_pending do
    transitions :to => :pending, :from => [:approved], :on_transition => :send_to_admin_queue
  end

   event :update_profile_approved do
    transitions :to => :approved, :from => [:pending], :on_transition => :update_current_profile
   end

   event :update_to_rejected do
    transitions :to => :rejected, :from => [:pending]
  end
end

def send_to_admin_queue
  //method to handlesending pending profiles to admin for approval
end

def update_current_profile
 //method to handle updated profiles with changes
end

end

A continuación, podría llamar el perfil User.update pendientes! o perfil User.update aprobado! para la transición entre los estados perfil y utilizar las devoluciones de llamada de transición para manejar el envío de los datos de edición entre el perfil y el perfil activo en espera.

Por lo que mediante el nested_attributes_for con su forma actual, no creo que es un truco, que he usado también para actualizar atributos anidados y trabajaría bien. En este caso, sin embargo puede que no necesite demasiado ya que tiene 2 perfiles (uno público, uno pendiente).

Es sólo una idea! Pensando en voz alta aquí!

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top