• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

hazendaz / scriptable-dataset / 630

22 Mar 2026 02:24AM UTC coverage: 90.323%. Remained the same
630

push

github

hazendaz
[mvn] Update maven wrapper

23 of 26 branches covered (88.46%)

Branch coverage included in aggregate %.

89 of 98 relevant lines covered (90.82%)

0.91 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

93.75
/src/main/java/de/gmorling/scriptabledataset/ScriptableTable.java
1
/*
2
 * SPDX-License-Identifier: Apache-2.0
3
 * Copyright 2011-2026 Hazendaz
4
 */
5
package de.gmorling.scriptabledataset;
6

7
import de.gmorling.scriptabledataset.handlers.ScriptInvocationHandler;
8
import de.gmorling.scriptabledataset.handlers.StandardHandlerConfig;
9

10
import java.util.ArrayList;
11
import java.util.Collections;
12
import java.util.HashMap;
13
import java.util.List;
14
import java.util.Map;
15
import java.util.Map.Entry;
16

17
import javax.script.ScriptEngine;
18
import javax.script.ScriptEngineManager;
19
import javax.script.ScriptException;
20

21
import org.dbunit.dataset.DataSetException;
22
import org.dbunit.dataset.ITable;
23
import org.dbunit.dataset.ITableMetaData;
24
import org.slf4j.Logger;
25
import org.slf4j.LoggerFactory;
26

27
/**
28
 * ITable implementation, that allows the usage of script statements as field values.
29
 */
30
public class ScriptableTable implements ITable {
31

32
    /** The logger. */
33
    private final Logger logger = LoggerFactory.getLogger(ScriptableTable.class);
1✔
34

35
    /** The wrapped. */
36
    private ITable wrapped;
37

38
    /** The engines by prefix. */
39
    private Map<String, ScriptEngine> enginesByPrefix = new HashMap<>();
1✔
40

41
    /** The handlers by prefix. */
42
    private Map<String, List<ScriptInvocationHandler>> handlersByPrefix = new HashMap<>();
1✔
43

44
    /**
45
     * Creates a new ScriptableTable.
46
     *
47
     * @param wrapped
48
     *            The ITable to be wrapped by this scriptable table. May not be null.
49
     * @param configurations
50
     *            An list with configurations
51
     */
52
    public ScriptableTable(ITable wrapped, List<ScriptableDataSetConfig> configurations) {
1✔
53

54
        this.wrapped = wrapped;
1✔
55

56
        ScriptEngineManager manager = new ScriptEngineManager();
1✔
57

58
        // load the engines
59
        for (ScriptableDataSetConfig oneConfig : configurations) {
1✔
60

61
            ScriptEngine engine = manager.getEngineByName(oneConfig.getLanguageName());
1✔
62

63
            if (engine == null) {
1✔
64
                throw new RuntimeException(
1✔
65
                        "No scripting engine found for language \"" + oneConfig.getLanguageName() + "\".");
1✔
66
            }
67
            enginesByPrefix.put(oneConfig.getPrefix(), engine);
1✔
68

69
            List<ScriptInvocationHandler> handlers = getAllHandlers(oneConfig);
1✔
70

71
            for (ScriptInvocationHandler oneHandler : handlers) {
1✔
72
                oneHandler.setScriptEngine(engine);
1✔
73
            }
1✔
74

75
            handlersByPrefix.put(oneConfig.getPrefix(), handlers);
1✔
76

77
            logger.info("Registered scripting engine {} for language {}.", engine, oneConfig.getLanguageName());
1✔
78
        }
1✔
79
    }
1✔
80

81
    @Override
82
    public int getRowCount() {
83
        return wrapped.getRowCount();
×
84
    }
85

86
    @Override
87
    public ITableMetaData getTableMetaData() {
88
        return wrapped.getTableMetaData();
1✔
89
    }
90

91
    @Override
92
    public Object getValue(int row, String column) throws DataSetException {
93

94
        Object theValue = wrapped.getValue(row, column);
1✔
95

96
        // only strings can be processed
97
        if (theValue instanceof String script) {
1!
98

99
            for (Entry<String, ScriptEngine> oneEntry : enginesByPrefix.entrySet()) {
1✔
100

101
                String prefix = oneEntry.getKey();
1✔
102

103
                // found engine for prefix
104
                if (script.startsWith(prefix)) {
1✔
105

106
                    ScriptEngine engine = oneEntry.getValue();
1✔
107
                    script = script.substring(prefix.length());
1✔
108

109
                    List<ScriptInvocationHandler> handlers = handlersByPrefix.get(oneEntry.getKey());
1✔
110

111
                    // preInvoke
112
                    for (ScriptInvocationHandler handler : handlers) {
1✔
113
                        script = handler.preInvoke(script);
1✔
114
                    }
1✔
115

116
                    logger.debug("Executing script: {}", script);
1✔
117

118
                    // the actual script evaluation
119
                    try {
120
                        theValue = engine.eval(script);
1✔
121
                    } catch (ScriptException e) {
×
122
                        throw new RuntimeException(e);
×
123
                    }
1✔
124

125
                    // call postInvoke in reversed order
126
                    Collections.reverse(handlers);
1✔
127
                    for (ScriptInvocationHandler handler : handlers) {
1✔
128
                        theValue = handler.postInvoke(theValue);
1✔
129
                    }
1✔
130
                }
131
            }
1✔
132
        }
133

134
        return theValue;
1✔
135
    }
136

137
    /**
138
     * Returns a list with all standard handlers registered for the language of the config and all handlers declared in
139
     * the config itself.
140
     *
141
     * @param config
142
     *            A config object.
143
     *
144
     * @return A list with handlers. Never null.
145
     */
146
    private List<ScriptInvocationHandler> getAllHandlers(ScriptableDataSetConfig config) {
147

148
        List<ScriptInvocationHandler> theValue = new ArrayList<>(
1✔
149
                StandardHandlerConfig.getStandardHandlersByLanguage(config.getLanguageName()));
1✔
150

151
        // custom handlers
152
        theValue.addAll(config.getHandlers());
1✔
153

154
        return theValue;
1✔
155
    }
156
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc