Pergunta

Eu estou querendo saber se é possível criar um temmuitos Relacionamento em um Modelo que utiliza o ID do usuário logado.

Exemplo:Uma dica que tem muitas votações (de diferentes usuários).Isso é fácil:

public $hasMany = array(
   'TipVoting' => array(
        'className' => 'TipVoting',
        'foreignKey' => 'tip_id',
        'dependent' => false,
        'conditions' => '',
        'fields' => '',
        'order' => '',
        'limit' => '',
        'offset' => '',
        'exclusive' => '',
        'finderQuery' => '',
        'counterQuery' => ''
    ));

Agora eu quero ter todas as Dicas, mas quero saber se o usuário conectado tens votado esta Dica já.Então, eu gostaria de criar um Relacionamento que se parece com isso:

public $hasMany = array(
   'MyTipVoting' => array(
        'className' => 'TipVoting',
        'foreignKey' => 'tip_id',
        'dependent' => false,
        'conditions' => array('TipVoting.user_id' => $loggedinUser_id),
        'fields' => '',
        'order' => '',
        'limit' => '',
        'offset' => '',
        'exclusive' => '',
        'finderQuery' => '',
        'counterQuery' => ''
    )
);

Como faço para obter o $loggedinUser_id para este Modelo?Ou isso é uma má maneira de implementar este problema?Eu deveria, ao invés de ir para uma área separada encontrar na TipVoting Modelo?

Qualquer idéias?

Obrigado!

Foi útil?

Solução

Use o comportamento contêntico. http://book.cakephp.org/view/474/containable

Você não deseja definir um relacionamento diferente, só deseja filtrar por critérios associados. O CONTELEBLE permitirá que você faça isso.

Com apenas o relacionamento de votos de ponta, em seu modelo, faça isso:

var $actsAs = array( 'Containable' );

Na ação do seu controlador, faça isso:

$this->TipVoting->find( 'all', array( 
 'contain' => array( 
   'Vote' => array( 
    'conditions' => array( 
      'TipVoting.user_id' => $this->Auth->User('id') ), 
    'order' => 'TipVoting.id DESC' ) ) );

Outras dicas

Se eu entendi a pergunta, o que você está realmente depois é uma maneira de definir a condição uma vez em vez de um meio para definir uma associação condição específica.O Containable comportamento iria lidar com a última, mas não o primeiro.Para que fim...

Eu não estou ciente de qualquer forma utilizar os valores da variável em sua juntar definição.Uma vez que estas são variáveis de classe, eu suspeito que não pode ser feito (isenção de responsabilidade:Eu ainda não tentei).Você também tem a complexidade de tentar acessar o que é, normalmente, uma sessão de valor (usuário autorizado) no nível do modelo, algo de um MVC não-não no sentido estrito.

O que eu tenho feito para atender necessidades semelhantes é uma combinação de coisas é a seguinte:

Eu uso o meu AppController para encaminhar o usuário autenticado informações:

# AppController
# You may or may not want to use the conditional
if( !empty( $this->data ) ) {
  $this->data['User'] = $this->Auth->user();
}

Em seu modelo, criar uma beforeFind() de retorno de chamada que irá modificar a estrutura de uma consulta:

# Your model, e.g. TipVoting
# The data[] array will probably be keyed differently
public function beforeFind( $query ) {
  if( array_key_exists( 'active', $this->_schema ) ) {
    $conditions = !empty( $query['conditions'] ) ? $query['conditions'] : array();

    if( !is_array( $conditions ) ) {
      $conditions = array( $conditions );
    }

    if( !isset ( $conditions['user_id'] ) && !isset( $conditions[$this->alias . '.user_id'] ) ) {
      $conditions[$this->alias . '.user_id'] = $this->data['User']['Administrator'];
    }

    $query['conditions'] = $conditions;
  }

  return $query;
}

Esse código é apenas um fragmento que atende a uma necessidade semelhantes para vocês, então não pode trabalhar diretamente, mas deve dar-lhe uma ideia do que é possível e eu acho que pode até ser muito próximo do que você está depois.Apenas esteja ciente de que você provavelmente terá que fazer algumas mudanças aqui e ali.

A chave é que você está mantendo o "bom" MVC estrutura de encaminhamento de informações de sessão para o modelo de forma explícita (em vez de perguntar o modelo para acessá-lo diretamente), enquanto a definição de sua condição de consulta para usar uma sessão de valor de todos os registros de tempo do modelo são obtidas a menos que um usuário-centrada no estado já está envolvido.

Não é um ajuste perfeito para o que você está depois, mas não deve demorar muito para adequá-lo às suas necessidades.

Tente usar o BindModel dos AppControllers antes do Filter.

...
public function beforeFilter( ){
    parent::beforeFilter( );
    if( $this->Auth->user( )){
        $this->User->bindModel(
            'hasMany' => array(
                'MyTipVoting' => array(
                    'className' => 'TipVoting',
                    'foreignKey' => 'tip_id',
                    'conditions' => array(
                        'MyTipVoting.user_id' => $this->Auth->user( 'id' ),
                        //note the use of the aliased name here, not TipVoting but MyTipVoting
                        ...
                    ),
                    ...
                ),
                ...
            ),
        );
    }
}
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top