hibernate/hibernate-orm · error · MappingException

<many-to-any /> mapping [%s] needs to specify 2 or more colu

Error message

<many-to-any /> mapping [%s] needs to specify 2 or more columns

What it means

<map-key-many-to-any/> maps a <map> whose key is a polymorphic reference. Such a key needs at least two relational values: the first column is the discriminator (resolved through meta-type) and the rest form the foreign key. PluralAttributeMapKeyManyToAnySourceImpl aborts bootstrap when fewer than two column/formula definitions are supplied for the key.

Source

Thrown at hibernate-core/src/main/java/org/hibernate/boot/model/source/internal/hbm/PluralAttributeMapKeyManyToAnySourceImpl.java:82

					@Override
					public String getSourceName() {
						return null;
					}

					@Override
					public List getColumnOrFormulaElements() {
						return jaxbMapKeyManyToAnyMapping.getColumn();
					}
				}
		);

		// the list of relational values should contain 2 or more values:
		//		* the first represents the discriminator
		//		* the rest represent the fk

		if ( relationalValueSources.size() < 2 ) {
			throw new MappingException(
					String.format(
							Locale.ENGLISH,
							"<many-to-any /> mapping [%s] needs to specify 2 or more columns",
							pluralAttributeSource.getAttributeRole().getFullPath()
					),
					mappingDocument.getOrigin()
			);
		}

		this.discriminatorSource = new AnyDiscriminatorSource() {
			private final HibernateTypeSource discriminatorTypeSource = new HibernateTypeSourceImpl( jaxbMapKeyManyToAnyMapping.getMetaType() );
			private final RelationalValueSource discriminatorRelationalValueSource = relationalValueSources.get( 0 );

			// the DTD/XSD currently do not allow discriminator mapping here
			private final Map<String,String> discriminatorValueMapping = Collections.emptyMap();
//		this.discriminatorValueMapping = new HashMap<String, String>();
//		for ( JaxbHbmAnyValueMappingType valueMapping : jaxbMapKeyManyToAnyMapping.getMetaValue() ) {
//			discriminatorValueMapping.put(

View on GitHub (pinned to fad1729dce)

Solutions

  1. Declare two or more columns inside <map-key-many-to-any>: the first is the discriminator, the rest are the fk of the referenced entity
  2. Verify meta-type/id-type and any <meta-value .../> mappings resolve the discriminator values to entity names
  3. Consider remodelling: an embeddable or dedicated association table is often simpler than a polymorphic map key

Example fix

// before
<map name='refs' table='refs'>
    <map-key-many-to-any meta-type='string' id-type='long'>
        <column name='ref_id'/>
    </map-key-many-to-any>
    ...
</map>

// after
<map name='refs' table='refs'>
    <map-key-many-to-any meta-type='string' id-type='long'>
        <column name='ref_type'/>
        <column name='ref_id'/>
    </map-key-many-to-any>
    ...
</map>
Defensive patterns

Strategy: validation

Validate before calling

// Pre-flight: every <map-key-many-to-any> must declare >= 2 columns
var key = (org.w3c.dom.Element) doc.getElementsByTagName("map-key-many-to-any").item(0);
int n = key.getElementsByTagName("column").getLength();
if (n < 2)
    throw new IllegalStateException("map-key-many-to-any needs discriminator + fk columns, found " + n);

Try / catch

catch (org.hibernate.boot.MappingException e) at Metadata build: the message carries the map's attribute role - locate the <map-key-many-to-any> element and add the discriminator column first, then the fk column(s)

Prevention

When it happens

Trigger: A <map> mapping containing <map-key-many-to-any meta-type='string' id-type='long'> with zero or one <column> child, so the built relational value source list has size < 2.

Common situations: Polymorphic map keys are rare and usually come from old Hibernate 2/3-era mappings or interface-keyed domain models; converting a normal <map-key> to polymorphic without altering the table; assuming the fk column alone identifies the key entity.

Related errors


AI-assisted analysis of hibernate/hibernate-orm@fad1729dce (2026-08-22). Data as JSON: /api/errors/89a79a66e7e3756f. Report an issue: GitHub.