Vaadin Grid设置列时报无法解析KPI属性的IllegalArgumentException
异常产生原因
Vaadin 传入Bean类型自动绑定Grid列的模式,底层依赖JDK标准的JavaBean内省机制解析类属性,不会直接读取类的成员变量,你的代码完全不符合该机制的解析要求,具体问题点:
- 类本身没有加
public修饰符,是包级访问权限,属性解析器无法正常访问类结构。 - 类没有提供public无参构造方法,不符合JavaBean的实例化要求。
- 所有字段都只声明了包级访问权限,没有编写符合命名规范的public getter方法,解析器根本识别不到任何可绑定的属性。
- 字段名
KPI全大写,就算补写getter也容易踩JavaBean内省的命名规则坑:内省工具对属性名做首字母转换时,如果名称前两个字符都是大写,不会做首字母小写处理,很容易出现属性名不匹配的问题。
修复方案
你可以按照JavaBean规范修改类定义,也可以改用手动配置列的方式绕开自动解析限制,两种方案都可以:
方案1:遵循JavaBean规范修改类,保留自动配置列的写法
- 给
ClientInformation类加public修饰符,添加public无参构造方法。 - 将全大写的
KPI字段改为小驼峰命名kpi,所有字段改为private访问权限,为每个字段添加符合命名规范的public getter/setter方法。 - 把Grid列配置里的
"KPI"改为对应属性名"kpi"。
修正后的类代码:
import com.vaadin.flow.component.HorizontalLayout; // 添加public修饰符 public class ClientInformation { // 字段改为private,KPI修正为小驼峰kpi private String kpi; private String clientsLastYear; private String clientsLastMonth; private String clientsCurrentMonth; private HorizontalLayout percentageMoM; private HorizontalLayout percentageYoY; // 必须添加public无参构造 public ClientInformation() {} // 保留全参构造方便业务赋值 public ClientInformation(String kpi, String clientsLastYear, String clientsLastMonth, String clientsCurrentMonth, HorizontalLayout percentageMoM, HorizontalLayout percentageYoY) { this.kpi = kpi; this.clientsLastYear = clientsLastYear; this.clientsLastMonth = clientsLastMonth; this.clientsCurrentMonth = clientsCurrentMonth; this.percentageMoM = percentageMoM; this.percentageYoY = percentageYoY; } // 所有字段添加标准getter/setter public String getKpi() { return kpi; } public void setKpi(String kpi) { this.kpi = kpi; } public String getClientsLastYear() { return clientsLastYear; } public void setClientsLastYear(String clientsLastYear) { this.clientsLastYear = clientsLastYear; } public String getClientsLastMonth() { return clientsLastMonth; } public void setClientsLastMonth(String clientsLastMonth) { this.clientsLastMonth = clientsLastMonth; } public String getClientsCurrentMonth() { return clientsCurrentMonth; } public void setClientsCurrentMonth(String clientsCurrentMonth) { this.clientsCurrentMonth = clientsCurrentMonth; } public HorizontalLayout getPercentageMoM() { return percentageMoM; } public void setPercentageMoM(HorizontalLayout percentageMoM) { this.percentageMoM = percentageMoM; } public HorizontalLayout getPercentageYoY() { return percentageYoY; } public void setPercentageYoY(HorizontalLayout percentageYoY) { this.percentageYoY = percentageYoY; } }
修正后的Grid配置代码:
Grid<ClientInformation> clientInfoGrid = new Grid<>(ClientInformation.class); // 把KPI改为修正后的属性名kpi clientInfoGrid.setColumns("kpi", "clientsLastYear", "clientsLastMonth", "clientsCurrentMonth", "percentageMoM", "percentageYoY");
方案2:手动配置列,绕开JavaBean自动解析限制
如果不想修改原有字段名和类结构,可以不用传入Bean类型让Grid自动解析属性,直接通过addColumn方法手动指定每一列的取值逻辑,这种方式不要求类符合JavaBean规范,示例代码:
// 不传ClientInformation.class,禁用自动属性解析 Grid<ClientInformation> clientInfoGrid = new Grid<>(); // 手动指定每一列的取值逻辑,直接引用字段或者写自定义取值逻辑都可以 clientInfoGrid.addColumn(item -> item.KPI).setHeader("KPI"); clientInfoGrid.addColumn(item -> item.clientsLastYear).setHeader("去年客户数"); clientInfoGrid.addColumn(item -> item.clientsLastMonth).setHeader("上月客户数"); clientInfoGrid.addColumn(item -> item.clientsCurrentMonth).setHeader("当月客户数"); clientInfoGrid.addComponentColumn(item -> item.percentageMoM).setHeader("环比"); clientInfoGrid.addComponentColumn(item -> item.percentageYoY).setHeader("同比");
注意:你代码里的percentageMoM和percentageYoY是HorizontalLayout组件类型,用自动属性解析的方式可能无法正常渲染,手动配置时用addComponentColumn来绑定组件列才是Vaadin推荐的写法。
内容的提问来源于stack exchange,提问作者Datta Dhonde
相关产品推荐
相关产品推荐

