Estratégia para mapeamento ManyToMany

Pessoal, gostaria de saber como fazem para mapear relacionamentos ManyToMany.

To achando meio bizarro a maneira que fiz, vou explicar:

Tenho as classes Equipe¹ e Operador², na Equipe declaro uma lista de Operadores e mapeio o get com a anotação @ManyToMany, na minha ViewEquipe£ eu utilizo uma lista populada de operadores nas checkboxes e o value como equipe.operadores.

Tá gravando tudo certinho, gera a tabela equipe_operador com as PK’s de cada entidade e é aí que tá o meu incomodo.

Como preciso manipular a tabela intermediária equipe_operador, acabo criando uma classe EquipeOperador, ou seja, pra criar a classe EquipeOperador acabo tendo que mapear uma PK da própria entidade EquipeOperador³, e to achando isso uma merda, pois a tabela gerada automaticamente com a anotação @ManyToMany não tem PK.

Quem tiver paciencia, poderia sanar minhas dúvidas:

  • Daria pra criar uma PK equipeOperadorId na anotação @ManyToMany?
  • Alguém poderia me explicar como eu poderia fazer isso de maneira bidirecional (OneToMany nas classes Equipe e Operador e ManyToOne na classe EquipeOperador)? Com essa abordagem, não usaria ManyToMany, como ficaria a minha lista de operadores e o value?
  • Existe outra maneira pra contornar essa situação?

Segue meu código:
¹ Classe Equipe

public class Equipe {

	private Integer equipeId;
	private String name;
	private List<Operador> operadores;	
	
	@Id
	@GeneratedValue(strategy = IDENTITY)
	@Column(name = "equipe_id")
	public Integer getEquipeId() {
		return equipeId;
	}
	
	@ManyToMany
	@JoinTable(name = "equipe_operador", 
	joinColumns = @JoinColumn(name = "equipe_id"), 
	inverseJoinColumns = @JoinColumn(name = "operador_id"))
	public List<Operador> getOperadores() {
		return operadores;
	}

	// construtor, get's, set's, hash e equals
}

² Classe Operador

public class Operador {

	private Integer operadorId;
	private String name;
	
	@Id
	@GeneratedValue(strategy = IDENTITY)
	@Column(name = "operador_id")
	public Integer getOperadorId() {
		return operadorId;
	}
	
	// construtor, get's, set's, hash e equals
}

³ Calsse EquipeOperador

public class EquipeOperador {
	
	private Integer equipeOperadorId;
	private Equipe equipe;
	private Operador operador;
	
	// Aqui que tá a merda!! <=================
	@Id
	@GeneratedValue(strategy = IDENTITY)
	@Column(name = "equipe_operador_id")
	public Integer getEquipeOperadorId() {
		return this.equipeOperadorId;
	}

	@ManyToOne(fetch = FetchType.LAZY)
	@JoinColumn(name = "equipe_id")
	@NotNull
	public Equipe getEquipe() {
		return this.equipe;
	}

	@ManyToOne(fetch = FetchType.LAZY)
	@JoinColumn(name = "operador_id", nullable = false)
	@NotNull
	public Operador getOperador() {
		return this.operador;
	}

	// construtor, get's, set's, hash e equals
}

£ ViewEquipe

<s:decorate id="operador">
	<ui:define name="label">Operadores</ui:define>
	<t:selectManyCheckbox value="#{equipe.operadores}">
		<s:selectItems var="_operador" value="#{operadores}"
			label="#{_operador.nome}" />
	</t:selectManyCheckbox>
</s:decorate>

Sei que são muitos dúvidas, mas to com medo de estar fazendo muita besteira.
Abraços!!!

Po pessoal, tenho certeza que alguém ja passou por isso!!

Resolvi remover o relacionamento many-to-many mesmo, mas agora preciso
de uma ajudinha:

  • Modelei uma classe de junção EquipeOperador, onde equipe e operador
    são @ManyToOne cada um e fiz um @Embeddable para ter uma chave
    composta.
  • Modelei a classe Equipe sendo @OneToMany em relação à EquipeOperador
  • Modelei a classe Operador sendo @OneToMany em relação à
    EquipeOperador

Alguém pode me dizer se é assim mesmo?

Aí surgiram umas dúvidas:

  • Considerando que seja na app EquipeAction que eu escolha um ou
    muitos operadores, na minha classe Equipe teria que ter um atributo
    private List equipeOperadores, que é o atributo
    anotado como @OneToMany, certo? Ou seja, Equipe recebe uma lista de
    EquipeOperador…isso não deu certo!!

Eu tentei assim para popular minhas checkboxes:

List<EquipeOperador> equipeOperadores = entityManager.createQuery("select o from Operador o").getResultList();

List<EquipeOperador> equipeOperadores = entityManager.createQuery("select o from EquipeOperador as eo, Operador o where eo.operador.operadorId = o.operadorId").getResultList();

E qdo entrava na tela para add uma equipe dava esse erro: Value
binding '#{equipeOperadores}'of UISelectItems with component-path …
does not reference an Object of type SelectItem, SelectItem[],
Collection or Map but of type : null