Skip to content

BeanPropertySet.get() misses interface-declared properties for Java records #24152

@nashkevichv

Description

@nashkevichv

Description of the bug

BeanPropertySet.get(T.class) does not correctly resolve all bean properties when T is a Java record that implements an interface with getter methods.
aProperties declared in the interface are silently omitted, whereas the same setup using a regular class works as expected.

Expected behavior

Both tests pass. BeanPropertySet should discover entityId, client, and server for both the record and the class.

Actual behavior: The record test fails — entityId (contributed by the implemented interface) is not discovered. The class test passes.

Minimal reproducible example

public static interface Entity<ID> {
     ID getEntityId();                                                                                                                                       
 }
                                                                                                                                                             
 // record — interface property missing                                                                                                                      
 public static record RecordWithInterface(String client, String server)
     implements Entity<String>                                                                                                                               
 {               
     @Override
     public final String getEntityId() {
         return this.server;
     }                                                                                                                                                       
 }
                                                                                                                                                             
 // class — works correctly
 public static class ClassWithInterface
     extends Object
     implements Entity<String>
 {
     private final String server;
     private final String client;
                                                                                                                                                             
     public ClassWithInterface() {
         this.server = "server";                                                                                                                             
         this.client = "client";
     }

     @Override
     public final String getEntityId() {
         return this.server + "_id";
     }
                                                                                                                                                             
     public String getClient() { return this.client; }
     public String getServer() { return this.server; }                                                                                                       
 }               

 @Test
 public final static void testBeanPropertySet_forRecordWithInterface() {
     final PropertySet<RecordWithInterface> set = BeanPropertySet.get(RecordWithInterface.class);                                                            
     assert set != null;
     assert set.getProperties().count() == 3;          // FAILS — entityId is missing                                                                        
     assert set.getProperty("entityId").isPresent();   // FAILS                                                                                              
     assert set.getProperty("server").isPresent();                                                                                                           
     assert set.getProperty("client").isPresent();                                                                                                           
 }                                                                                                                                                           
                 
 @Test
 public final static void testBeanPropertySet_forClassWithInterface() {
     final PropertySet<ClassWithInterface> set = BeanPropertySet.get(ClassWithInterface.class);
     assert set != null;                                                                                                                                     
     assert set.getProperties().count() == 3;          // PASSES
     assert set.getProperty("entityId").isPresent();   // PASSES                                                                                             
     assert set.getProperty("server").isPresent();
     assert set.getProperty("client").isPresent();                                                                                                           
 }

Versions

  • Vaadin / Flow version: 24.9.0
  • Java version: 17
  • OS version: any
  • Browser version (if applicable): does not matter
  • Application Server (if applicable):
  • IDE (if applicable):

Metadata

Metadata

Assignees

No one assigned

    Projects

    Status

    Inbox (needs triage)

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions