spring - 如何使用 setItems for grid 将数据添加到 Vaadin 中的 CRUD?
问题描述
我将向 Vaadin 中的 CRUD 组件添加数据。这是一个简单的问题。但是我遇到的问题是,我无法通过首先获取grid
对象然后将其项目设置给它来将数据添加到 CRUD。
这是我的 Vaadin 课程。这个类首先开始从 JPA Spring 数据库中获取数据。好的。那是有效的。并且数据被传输到一个名为的集合crudData
中。然后crudData
是众生设置crud.getGrid().setItems(crudData);
,这是行不通的。我假设如果我从 CRUD 获得网格,那么我也可以设置网格项,然后它们将显示在 CRUD 上......但没有......
@Data
public class StocksCrud {
private Crud<StockNames> crud;
private List<StockNames> crudData;
private StockNamesRepository stockNamesRepository;
private CrudEditor<StockNames> createStocksEditor() {
TextField stockName = new TextField("Name of the stock");
FormLayout form = new FormLayout(stockName);
Binder<StockNames> binder = new Binder<>(StockNames.class);
binder.bind(stockName, StockNames::getStockName, StockNames::setStockName);
return new BinderCrudEditor<>(binder, form);
}
public StocksCrud(StockNamesRepository stockNamesRepository) {
this.stockNamesRepository = stockNamesRepository;
// Fill the crud
crudData = new ArrayList<StockNames>();
for(StockNames stockName: stockNamesRepository.findAll()) {
crudData.add(new StockNames(stockName.getId(), stockName.getStockName()));
}
// Crate crud table
crud = new Crud<>(StockNames.class, createStocksEditor());
crud.getGrid().setItems(crudData); // This won't work
crud.addSaveListener(e -> saveStock(e.getItem()));
crud.addDeleteListener(e -> deleteStock(e.getItem()));
crud.getGrid().removeColumnByKey("id");
crud.addThemeVariants(CrudVariant.NO_BORDER);
}
private void deleteStock(StockNames stockNames) {
boolean exist = stockNamesRepository.existsBystockName(stockNames.getStockName());
if(exist == true) {
crudData.remove(stockNames);
stockNamesRepository.delete(stockNames);
}
}
private void saveStock(StockNames stockNames) {
System.out.println(stockNames == null);
System.out.println(stockNamesRepository == null);
boolean exist = stockNamesRepository.existsBystockName(stockNames.getStockName());
if(exist == false) {
crudData.add(stockNames);
stockNamesRepository.save(stockNames);
}
}
}
这是我的错误输出:
java.lang.ClassCastException: com.vaadin.flow.component.crud.CrudFilter cannot be cast to com.vaadin.flow.function.SerializablePredicate
我知道有一种方法可以通过使用数据提供程序类在 Vaadin 中将数据设置为 CRUD。但我不想用那个。这是....太多的代码。我想保持干净并用 Java 编写更少的代码。底部的示例:https ://vaadin.com/components/vaadin-crud/java-examples
@Entity
@Data
@NoArgsConstructor
public class StockNames implements Cloneable{
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private int id;
private String stockName;
public StockNames(int id, String stockName) {
this.id = id;
this.stockName = stockName;
}
}
更新:
这是我现在的代码
@Data
public class StocksCrud {
private Crud<StockNames> crud;
private List<StockNames> crudData;
private StockNamesRepository stockNamesRepository;
private CrudEditor<StockNames> createStocksEditor() {
TextField stockName = new TextField("Name of the stock");
FormLayout form = new FormLayout(stockName);
Binder<StockNames> binder = new Binder<>(StockNames.class);
binder.bind(stockName, StockNames::getStockName, StockNames::setStockName);
return new BinderCrudEditor<>(binder, form);
}
public StocksCrud(StockNamesRepository stockNamesRepository) {
this.stockNamesRepository = stockNamesRepository;
// Fill the crud
crudData = new ArrayList<StockNames>();
for(StockNames stockName: stockNamesRepository.findAll()) {
crudData.add(new StockNames(stockName.getId(), stockName.getStockName()));
}
// Create grid
Grid<StockNames> grid = new Grid<StockNames>();
grid.setItems(crudData);
// Crate crud table
crud = new Crud<>(StockNames.class, createStocksEditor());
crud.setGrid(grid);
crud.addSaveListener(e -> saveStock(e.getItem()));
crud.addDeleteListener(e -> deleteStock(e.getItem()));
//crud.getGrid().removeColumnByKey("id");
crud.addThemeVariants(CrudVariant.NO_BORDER);
}
private void deleteStock(StockNames stockNames) {
boolean exist = stockNamesRepository.existsBystockName(stockNames.getStockName());
if(exist == true) {
crudData.remove(stockNames);
stockNamesRepository.delete(stockNames);
}
}
private void saveStock(StockNames stockNames) {
System.out.println(stockNames == null);
System.out.println(stockNamesRepository == null);
boolean exist = stockNamesRepository.existsBystockName(stockNames.getStockName());
if(exist == false) {
crudData.add(stockNames);
stockNamesRepository.save(stockNames);
}
}
}
更新 2:
这给出了一个错误。
// Create grid
Grid<StockNames> grid = new Grid<StockNames>();
StockNames s1 = new StockNames(1, "HELLO");
crudData.add(s1);
grid.setItems(crudData);
// Crate crud table
crud = new Crud<>(StockNames.class, createStocksEditor());
crud.setGrid(grid);
crud.addSaveListener(e -> saveStock(e.getItem()));
crud.addDeleteListener(e -> deleteStock(e.getItem()));
crud.getGrid().removeColumnByKey(grid.getColumns().get(0).getKey());
crud.addThemeVariants(CrudVariant.NO_BORDER);
错误是:
java.lang.IndexOutOfBoundsException: Index: 0, Size: 0'
什么?我刚刚添加了一个对象。
解决方案
分配网格解决了这个问题
Grid<StockNames> grid=new Grid<>(StockNames.class);
crud = new Crud<>(StockNames.class,grid, createStocksEditor());
在您的代码示例中,您依赖于提供的默认实现Crud
,因此CrudGrid
正在创建。它的setDataProvider返回DataProvider<E,CrudFilter>
,而 Grid 的 DataProvider 是类型:(AbstractDataProvider<T, SerializablePredicate<T>>
这是因为您使用的是ListDataProvider
,它扩展了AbstractDataProvider<T, SerializablePredicate<T>>
)。这是错误状态:
java.lang.ClassCastException:com.vaadin.flow.component.crud。CrudFilter不能转换为 com.vaadin.flow.function。可序列化谓词
因此,如果您想通过网格分配值 - 您首先需要创建一个。否则,如文档中所示,您可以提供自定义数据提供者:PersonDataProvider
更新
这是我正在使用的示例代码。在我向 bean 添加一个无参数构造函数之后,在 Crud 中添加一个新项目是可行的:
import java.util.Random;
public class StockNames implements Cloneable{
Random rnd=new Random();
private int id;
private String stockName;
public StockNames(){
//You will an id generated automatically for you, but here is just an example
id=rnd.nextInt(12000);
}
public StockNames(int id, String stockName) {
this.id = id;
this.stockName = stockName;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getStockName() {
return stockName;
}
public void setStockName(String stockName) {
this.stockName = stockName;
}
}
和StockCrud
班级:
import com.vaadin.flow.component.crud.*;
import com.vaadin.flow.component.formlayout.FormLayout;
import com.vaadin.flow.component.grid.Grid;
import com.vaadin.flow.component.orderedlayout.VerticalLayout;
import com.vaadin.flow.component.textfield.TextField;
import com.vaadin.flow.data.binder.Binder;
import com.vaadin.flow.router.Route;
import java.util.ArrayList;
import java.util.List;
@Route("crudLayout")
public class StockCrud extends VerticalLayout {
private Crud<StockNames> crud;
private List<StockNames> crudData;
private CrudEditor<StockNames> createStocksEditor() {
TextField stockName = new TextField("Name of the stock");
FormLayout form = new FormLayout(stockName);
Binder<StockNames> binder = new Binder<>(StockNames.class);
binder.bind(stockName, StockNames::getStockName, StockNames::setStockName);
return new BinderCrudEditor<>(binder, form);
}
public StockCrud() {
// Fill the crud
crudData = new ArrayList<StockNames>();
for(int i=0;i<150;i++) {
crudData.add(new StockNames(i,"Name " + i));
}
// Crate crud table
Grid<StockNames> grid=new Grid<>(StockNames.class);
crud = new Crud<>(StockNames.class,grid, createStocksEditor());
//((CrudGrid )crud.getGrid()).setItems(crudData);
crud.getGrid().setItems(crudData); // This won't work
crud.addSaveListener(e -> saveStock(e.getItem()));
crud.addDeleteListener(e -> deleteStock(e.getItem()));
// crud.getGrid().removeColumnByKey("id");
crud.addThemeVariants(CrudVariant.NO_BORDER);
add(crud);
}
private void deleteStock(StockNames stockNames) {
// if(crudData.contains(stockNames)) {
crudData.remove(stockNames);
//}
}
private void saveStock(StockNames stockNames) {
System.out.println(stockNames == null);
if(!crudData.contains(stockNames)) {
crudData.add(stockNames);
}
}
}
推荐阅读
- asp.net-mvc - 如何阻止方法返回调用方法
- python - 基于 Python 的 Azure Functions 的虚拟环境
- shiro - 最新 1.6 Apache Shiro 发布问题
- javascript - DataTables from AJAX Call
- css - 如何让 div 列对齐?
- regex - 为什么某些正则表达式匹配没有被一一替换?
- java - 如何在java中转换父子类?
- sql-server - 基于 SQL Server 2019 的 PolyBase:IBM DB2 外部表
- python - 尝试使用 pyttsx3 冻结文件时出错 - 找不到模块 sapi5
- javascript - 是否可以根据 if 条件在 try catch 块中抛出异常以停止执行 try 块并开始执行 catch 块?