HHH-7545 : Aliases for a collection key and element column can collide causing one to be excluded

This commit is contained in:
Gail Badner 2012-08-23 01:06:38 -07:00
parent 07d154fbf2
commit 5327ac5396
7 changed files with 606 additions and 1 deletions

View File

@ -350,7 +350,7 @@ public abstract class AbstractCollectionPersister
iter = collection.getElement().getColumnIterator();
while ( iter.hasNext() ) {
Selectable selectable = (Selectable) iter.next();
elementColumnAliases[j] = selectable.getAlias( dialect );
elementColumnAliases[j] = selectable.getAlias( dialect, table );
if ( selectable.isFormula() ) {
Formula form = (Formula) selectable;
elementFormulaTemplates[j] = form.getTemplate( dialect, factory.getSqlFunctionRegistry() );

View File

@ -0,0 +1,119 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* Copyright (c) 2012, Red Hat Inc. or third-party contributors as
* indicated by the @author tags or express copyright attribution
* statements applied by the authors. All third-party contributions are
* distributed under license by Red Hat Inc.
*
* This copyrighted material is made available to anyone wishing to use, modify,
* copy, or redistribute it subject to the terms and conditions of the GNU
* Lesser General Public License, as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
* for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this distribution; if not, write to:
* Free Software Foundation, Inc.
* 51 Franklin Street, Fifth Floor
* Boston, MA 02110-1301 USA
*/
package org.hibernate.test.collectionalias;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.Id;
import javax.persistence.OneToMany;
/**
* @author Dave Stephan
*/
@Entity
public class ATable implements Serializable
{
private Integer firstId;
private List<TableB> tablebs = new ArrayList<TableB>();
public ATable()
{
}
/** minimal constructor */
public ATable(Integer firstId)
{
this.firstId = firstId;
}
@Id
@Column(name = "idcolumn", nullable = false)
public Integer getFirstId()
{
return this.firstId;
}
public void setFirstId(Integer firstId)
{
this.firstId = firstId;
}
@Override
public int hashCode()
{
final int prime = 31;
int result = 1;
result = prime * result + ((firstId == null) ? 0 : firstId.hashCode());
result = prime * result + ((tablebs == null) ? 0 : tablebs.hashCode());
return result;
}
@Override
public boolean equals(Object obj)
{
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
ATable other = (ATable) obj;
if (firstId == null)
{
if (other.firstId != null)
return false;
}
else if (!firstId.equals(other.firstId))
return false;
if (tablebs == null)
{
if (other.tablebs != null)
return false;
}
else if (!tablebs.equals(other.tablebs))
return false;
return true;
}
@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, mappedBy = "tablea")
public List<TableB> getTablebs()
{
return tablebs;
}
public void setTablebs(List<TableB> tablebs)
{
this.tablebs = tablebs;
}
}

View File

@ -0,0 +1,77 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* Copyright (c) 2012, Red Hat Inc. or third-party contributors as
* indicated by the @author tags or express copyright attribution
* statements applied by the authors. All third-party contributions are
* distributed under license by Red Hat Inc.
*
* This copyrighted material is made available to anyone wishing to use, modify,
* copy, or redistribute it subject to the terms and conditions of the GNU
* Lesser General Public License, as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
* for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this distribution; if not, write to:
* Free Software Foundation, Inc.
* 51 Franklin Street, Fifth Floor
* Boston, MA 02110-1301 USA
*/
package org.hibernate.test.collectionalias;
import org.junit.Test;
import org.hibernate.Session;
import org.hibernate.testing.TestForIssue;
import org.hibernate.testing.junit4.BaseCoreFunctionalTestCase;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertSame;
/**
* @author Dave Stephan
* @author Gail Badner
*/
public class CollectionAliasTest extends BaseCoreFunctionalTestCase {
@TestForIssue( jiraKey = "HHH-7545" )
@Test
public void test() {
Session s = openSession();
s.getTransaction().begin();
ATable aTable = new ATable( 1 );
TableB tableB = new TableB(
new TableBId( 1, "a", "b" )
);
aTable.getTablebs().add( tableB );
tableB.setTablea( aTable );
s.save( aTable );
s.getTransaction().commit();
s.close();
s = openSession();
aTable = (ATable) s.createQuery( "select distinct tablea from ATable tablea LEFT JOIN FETCH tablea.tablebs " ).uniqueResult();
assertEquals( new Integer( 1 ), aTable.getFirstId() );
assertEquals( 1, aTable.getTablebs().size() );
tableB = aTable.getTablebs().get( 0 );
assertSame( aTable, tableB.getTablea() );
assertEquals( new Integer( 1 ), tableB.getId().getFirstId() );
assertEquals( "a", tableB.getId().getSecondId() );
assertEquals( "b", tableB.getId().getThirdId() );
}
@Override
protected Class[] getAnnotatedClasses() {
return new Class[] {
TableBId.class,
TableB.class,
TableA.class,
ATable.class
};
}
}

View File

@ -0,0 +1,45 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* Copyright (c) 2012, Red Hat Inc. or third-party contributors as
* indicated by the @author tags or express copyright attribution
* statements applied by the authors. All third-party contributions are
* distributed under license by Red Hat Inc.
*
* This copyrighted material is made available to anyone wishing to use, modify,
* copy, or redistribute it subject to the terms and conditions of the GNU
* Lesser General Public License, as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
* for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this distribution; if not, write to:
* Free Software Foundation, Inc.
* 51 Franklin Street, Fifth Floor
* Boston, MA 02110-1301 USA
*/
package org.hibernate.test.collectionalias;
/**
* The bug fixed by HHH-7545 showed showed different results depending on the order
* in which entity mappings were processed.
*
* This mappings are in the opposite order here than in CollectionAliasTest.
*
* @Author Gail Badner
*/
public class ReorderedMappingsCollectionAliasTest extends CollectionAliasTest {
@Override
protected Class[] getAnnotatedClasses() {
return new Class[] {
ATable.class,
TableA.class,
TableB.class,
TableBId.class,
};
}
}

View File

@ -0,0 +1,113 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* Copyright (c) 2012, Red Hat Inc. or third-party contributors as
* indicated by the @author tags or express copyright attribution
* statements applied by the authors. All third-party contributions are
* distributed under license by Red Hat Inc.
*
* This copyrighted material is made available to anyone wishing to use, modify,
* copy, or redistribute it subject to the terms and conditions of the GNU
* Lesser General Public License, as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
* for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this distribution; if not, write to:
* Free Software Foundation, Inc.
* 51 Franklin Street, Fifth Floor
* Boston, MA 02110-1301 USA
*/
package org.hibernate.test.collectionalias;
import javax.persistence.Entity;
import javax.persistence.Id;
/**
* @author Dave Stephan
*/
@Entity
public class TableA
{
@Id
private int id;
private String test;
private String test2;
@Override
public int hashCode()
{
final int prime = 31;
int result = 1;
result = prime * result + id;
result = prime * result + ((test == null) ? 0 : test.hashCode());
result = prime * result + ((test2 == null) ? 0 : test2.hashCode());
return result;
}
@Override
public boolean equals(Object obj)
{
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
TableA other = (TableA) obj;
if (id != other.id)
return false;
if (test == null)
{
if (other.test != null)
return false;
}
else if (!test.equals(other.test))
return false;
if (test2 == null)
{
if (other.test2 != null)
return false;
}
else if (!test2.equals(other.test2))
return false;
return true;
}
public String getTest2()
{
return test2;
}
public void setTest2(String test2)
{
this.test2 = test2;
}
public String getTest()
{
return test;
}
public void setTest(String test)
{
this.test = test;
}
public int getId()
{
return id;
}
public void setId(int id)
{
this.id = id;
}
}

View File

@ -0,0 +1,118 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* Copyright (c) 2012, Red Hat Inc. or third-party contributors as
* indicated by the @author tags or express copyright attribution
* statements applied by the authors. All third-party contributions are
* distributed under license by Red Hat Inc.
*
* This copyrighted material is made available to anyone wishing to use, modify,
* copy, or redistribute it subject to the terms and conditions of the GNU
* Lesser General Public License, as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
* for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this distribution; if not, write to:
* Free Software Foundation, Inc.
* 51 Franklin Street, Fifth Floor
* Boston, MA 02110-1301 USA
*/
package org.hibernate.test.collectionalias;
import java.io.Serializable;
import javax.persistence.AttributeOverride;
import javax.persistence.AttributeOverrides;
import javax.persistence.Column;
import javax.persistence.EmbeddedId;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.JoinColumn;
import javax.persistence.JoinColumns;
import javax.persistence.ManyToOne;
/**
* @author Dave Stephan
*/
@Entity
public class TableB implements Serializable
{
private TableBId id;
private ATable tablea;
public TableB() {
}
/** full constructor */
public TableB(TableBId id) {
this.id = id;
}
// Property accessors
@EmbeddedId
@AttributeOverrides( {
@AttributeOverride(name = "firstId", column = @Column(name = "idcolumn", nullable = false)),
@AttributeOverride(name = "secondId", column = @Column(name = "idcolumn_second", nullable = false, length = 50)),
@AttributeOverride(name = "thirdId", column = @Column(name = "thirdcolumn", nullable = false, length = 20)) })
public TableBId getId() {
return this.id;
}
@Override
public int hashCode()
{
final int prime = 31;
int result = 1;
result = prime * result + ((id == null) ? 0 : id.hashCode());
result = prime * result + ((tablea == null) ? 0 : tablea.hashCode());
return result;
}
@Override
public boolean equals(Object obj)
{
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
TableB other = (TableB) obj;
if (id == null)
{
if (other.id != null)
return false;
}
else if (!id.equals(other.id))
return false;
if (tablea == null)
{
if (other.tablea != null)
return false;
}
else if (!tablea.equals(other.tablea))
return false;
return true;
}
public void setId(TableBId id) {
this.id = id;
}
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumns( { @JoinColumn(name = "idcolumn", referencedColumnName = "idcolumn", nullable = false, insertable = false, updatable = false) })
public ATable getTablea() {
return tablea;
}
public void setTablea(ATable tablea) {
this.tablea = tablea;
}
}

View File

@ -0,0 +1,133 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* Copyright (c) 2012, Red Hat Inc. or third-party contributors as
* indicated by the @author tags or express copyright attribution
* statements applied by the authors. All third-party contributions are
* distributed under license by Red Hat Inc.
*
* This copyrighted material is made available to anyone wishing to use, modify,
* copy, or redistribute it subject to the terms and conditions of the GNU
* Lesser General Public License, as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
* for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this distribution; if not, write to:
* Free Software Foundation, Inc.
* 51 Franklin Street, Fifth Floor
* Boston, MA 02110-1301 USA
*/
package org.hibernate.test.collectionalias;
import java.io.Serializable;
import javax.persistence.Column;
import javax.persistence.Embeddable;
/**
* @author Dave Stephan
*/
@Embeddable
public class TableBId implements Serializable
{
private static final long serialVersionUID = 1L;
// Fields
private Integer firstId;
private String secondId;
private String thirdId;
// Constructors
/** default constructor */
public TableBId() {
}
/** full constructor */
public TableBId(Integer firstId, String secondId, String thirdId) {
this.firstId = firstId;
this.secondId = secondId;
this.thirdId = thirdId;
}
// Property accessors
@Column(name = "idcolumn", nullable = false)
public Integer getFirstId() {
return this.firstId;
}
public void setFirstId(Integer firstId) {
this.firstId = firstId;
}
@Column(name = "idcolumn_second", nullable = false, length = 50)
public String getSecondId() {
return this.secondId;
}
public void setSecondId(String secondId) {
this.secondId = secondId;
}
@Column(name = "thirdcolumn", nullable = false, length = 50)
public String getThirdId() {
return this.thirdId;
}
public void setThirdId(String thirdId) {
this.thirdId = thirdId;
}
@Override
public int hashCode()
{
final int prime = 31;
int result = 1;
result = prime * result + ((firstId == null) ? 0 : firstId.hashCode());
result = prime * result + ((secondId == null) ? 0 : secondId.hashCode());
result = prime * result + ((thirdId == null) ? 0 : thirdId.hashCode());
return result;
}
@Override
public boolean equals(Object obj)
{
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
TableBId other = (TableBId) obj;
if (firstId == null)
{
if (other.firstId != null)
return false;
}
else if (!firstId.equals(other.firstId))
return false;
if (secondId == null)
{
if (other.secondId != null)
return false;
}
else if (!secondId.equals(other.secondId))
return false;
if (thirdId == null)
{
if (other.thirdId != null)
return false;
}
else if (!thirdId.equals(other.thirdId))
return false;
return true;
}
}