Reputation: 299
I am new to Groovy and DSLs, so I am bit fuzzy on the concepts. I have created a DSL, based on an example I've seen elsewhere:
class XSSFWorkbook {
XSSFSheet createSheet() {
return new XSSFSheet();
}
}
class XSSFSheet {
XSSFRow createRow(int rowIdx) {
return new XSSFRow(rowIdx);
}
}
class XSSFRow {
int rowIdx;
XSSFRow(int p_RowIdx) {
rowIdx = p_RowIdx
}
XSSFCell createCell(int cellIdx) {
return new XSSFCell(rowIdx);
}
}
class XSSFCell {
int cellIdx;
String cellValue;
XSSFCell(int p_CellIdx) {
cellIdx = p_CellIdx
}
}
class ExcelBuilder {
static XSSFWorkbook build(@DelegatesTo(Workbook) Closure callable) {
XSSFWorkbook wb = new XSSFWorkbook()
callable.resolveStrategy = Closure.DELEGATE_FIRST
callable.delegate = new Workbook(wb)
callable.call()
wb
}
}
class Workbook {
private final XSSFWorkbook wb
Workbook(XSSFWorkbook wb) {
this.wb = wb
}
XSSFSheet sheet(@DelegatesTo(Sheet) Closure callable) {
XSSFSheet sheet = wb.createSheet()
callable.resolveStrategy = Closure.DELEGATE_FIRST
callable.delegate = new Sheet(sheet)
callable.call()
sheet
}
}
class Sheet {
private final XSSFSheet sheet
private int rowIdx
Sheet(XSSFSheet sheet) {
this.sheet = sheet
this.rowIdx = 0
}
XSSFRow row(@DelegatesTo(Row) Closure callable) {
XSSFRow row = sheet.createRow(rowIdx)
callable.resolveStrategy = Closure.DELEGATE_FIRST
callable.delegate = new Row(row)
callable.call()
rowIdx++
row
}
}
class Row {
private final XSSFRow row
private int cellIdx
Row(XSSFRow row) {
this.row = row
this.cellIdx = 0
}
XSSFCell cell(Object value) {
XSSFCell cell = row.createCell(cellIdx)
cellIdx++
cell.setCellValue(value.toString())
cell
}
}
ExcelBuilder.build {
sheet {
row {
cell(1)
}
}
}
When I use Eclipse, I get the expected completion suggestions. For example, if I start trying to add another "row" element:
However, I want to limit my DSL to not include any other Groovy syntax. From what I've read so far, I need to use SecureASTCustomizer. But I am unclear if there is any way to use this so that my IDE (in this case Eclipse, but ideally any) is aware of the restrictions and highlights the offending code. For example, if I typed in the following:
ExcelBuilder.build {
sheet {
row {
cell(1)
}
}
def x = 1
println(x)
}
I would like the "def x = 1" and "println(x)" to be highlighted by my IDE as invalid in my DSL.
Upvotes: 0
Views: 21