diff --git a/docs/docs/assertions/snapshots.md b/docs/docs/assertions/snapshots.md index cacb91cd..8fb4228d 100644 --- a/docs/docs/assertions/snapshots.md +++ b/docs/docs/assertions/snapshots.md @@ -1,5 +1,5 @@ # Snapshots -:octicons-tag-24: 0.7.0 ยท +:octicons-tag-24: 0.7.0 Snapshots are a very useful tool whenever you want to make sure your output channels or output files not change unexpectedly. This feature is highly inspired by [Jest](https://jestjs.io/). @@ -38,6 +38,23 @@ When a snapshot test is failing due to an intentional implementation change, you nf-test test tests/main.nf.test --update-snapshot ``` +## Cleaning Obsolete Snapshots + +:octicons-tag-24: 0.8.0 + +Over time, snapshots can become outdated, leading to inconsistencies in your testing process. To help you manage obsolete snapshots, nf-test generates a list of these obsolete keys. +This list provides transparency into which snapshots are no longer needed and can be safely removed. + +Running your tests with the `--clean-snapshot`or `--wipe-snapshot` option removes the obsolete snapshots from the snapshot file. +This option is useful when you want to maintain the structure of your snapshot file but remove unused entries. +It ensures that your snapshot file only contains the snapshots required for your current tests, reducing file bloat and improving test performance. + +``` +nf-test test tests/main.nf.test --clean-snapshot +``` + +>:bulb: Obsolete snapshots can only be detected when running all tests in a test file simultaneously, and when all tests pass. If you run a single test or if tests are skipped, nf-test cannot detect obsolete snapshots. + ## More Examples It is also possible to include multiple objects into one snapshot: diff --git a/src/main/java/com/askimed/nf/test/commands/RunTestsCommand.java b/src/main/java/com/askimed/nf/test/commands/RunTestsCommand.java index 2d456e63..863c7343 100644 --- a/src/main/java/com/askimed/nf/test/commands/RunTestsCommand.java +++ b/src/main/java/com/askimed/nf/test/commands/RunTestsCommand.java @@ -55,6 +55,11 @@ public class RunTestsCommand extends AbstractCommand { @Option(names = { "--update-snapshot", "--updateSnapshot" }, description = "Use this flag to re-record every snapshot that fails during this test run.", required = false, showDefaultValue = Visibility.ALWAYS) private boolean updateSnapshot = false; + + @Option(names = { "--clean-snapshot", "--cleanSnapshot", "--wipe-snapshot", + "--wipeSnapshot" }, description = "Removes all obsolete snapshots.", required = false, showDefaultValue = Visibility.ALWAYS) + private boolean cleanSnapshot = false; + @Option(names = { "--lib" }, description = "Library extension path", required = false, showDefaultValue = Visibility.ALWAYS) private String lib = ""; @@ -148,6 +153,7 @@ public Integer execute() throws Exception { engine.setDebug(debug); engine.setWorkDir(workDir); engine.setUpdateSnapshot(updateSnapshot); + engine.setCleanSnapshot(cleanSnapshot); engine.setLibDir(libDir); engine.setPluginManager(manager); diff --git a/src/main/java/com/askimed/nf/test/core/AbstractTestSuite.java b/src/main/java/com/askimed/nf/test/core/AbstractTestSuite.java index 3949e5c0..acf7082f 100644 --- a/src/main/java/com/askimed/nf/test/core/AbstractTestSuite.java +++ b/src/main/java/com/askimed/nf/test/core/AbstractTestSuite.java @@ -5,6 +5,7 @@ import java.util.Vector; import com.askimed.nf.test.config.Config; +import com.askimed.nf.test.lang.extensions.SnapshotFile; public abstract class AbstractTestSuite implements ITestSuite { @@ -26,6 +27,10 @@ public abstract class AbstractTestSuite implements ITestSuite { private String directory = ""; + private SnapshotFile snapshotFile; + + private boolean failedTests = false; + private List tags = new Vector(); @Override @@ -135,6 +140,39 @@ public ITaggable getParent() { return null; } + @Override + public boolean hasSkippedTests() { + for (ITest test : getTests()) { + if (test.isSkipped()) { + return true; + } + } + return false; + } + + @Override + public SnapshotFile getSnapshot() { + if (snapshotFile == null) { + snapshotFile = SnapshotFile.loadByTestSuite(this); + } + return snapshotFile; + } + + @Override + public boolean hasSnapshotLoaded() { + return (snapshotFile != null); + } + + @Override + public void setFailedTests(boolean failedTests) { + this.failedTests = failedTests; + } + + @Override + public boolean hasFailedTests() { + return failedTests; + } + protected String makeAbsolute(String path) { return new File(directory, path).getAbsolutePath(); } diff --git a/src/main/java/com/askimed/nf/test/core/AnsiTestExecutionListener.java b/src/main/java/com/askimed/nf/test/core/AnsiTestExecutionListener.java index 4a1650b0..53fabad1 100644 --- a/src/main/java/com/askimed/nf/test/core/AnsiTestExecutionListener.java +++ b/src/main/java/com/askimed/nf/test/core/AnsiTestExecutionListener.java @@ -1,6 +1,7 @@ package com.askimed.nf.test.core; +import com.askimed.nf.test.lang.extensions.SnapshotFile; import com.askimed.nf.test.util.AnsiColors; import com.askimed.nf.test.util.AnsiText; @@ -16,6 +17,12 @@ public class AnsiTestExecutionListener implements ITestExecutionListener { private boolean debug = false; + private int updatedSnapshots; + + private int createdSnapshots; + + private int obsoleteSnapshots; + public static final int TEST_PADDING = 2; @Override @@ -33,6 +40,22 @@ public void testPlanExecutionFinished() { double executionTime = ((end - start) / 1000.0); System.out.println(); + + if ((updatedSnapshots + createdSnapshots + obsoleteSnapshots) > 0) { + System.out.println(); + System.out.println("Snapshot Summary:"); + } + if (updatedSnapshots > 0) { + System.out.println(AnsiText.padding(updatedSnapshots + " updated", TEST_PADDING)); + } + if (createdSnapshots > 0) { + System.out.println(AnsiText.padding(createdSnapshots + " created", TEST_PADDING)); + } + + if (obsoleteSnapshots > 0) { + System.out.println(AnsiColors.yellow(AnsiText.padding(obsoleteSnapshots + " obsolete", TEST_PADDING))); + } + System.out.println(); if (failed > 0) { @@ -63,6 +86,46 @@ public void testSuiteExecutionStarted(ITestSuite testSuite) { @Override public void testSuiteExecutionFinished(ITestSuite testSuite) { + if (!testSuite.hasSnapshotLoaded()) { + return; + } + + SnapshotFile snapshot = testSuite.getSnapshot(); + if ((snapshot.getUpdatedSnapshots().size() + snapshot.getCreatedSnapshots().size() + + snapshot.getObsoleteSnapshots().size()) > 0 || testSuite.hasSkippedTests()) { + System.out.println(AnsiText.padding("Snapshots:", TEST_PADDING)); + } + if (snapshot.getUpdatedSnapshots().size() > 0) { + System.out.println(AnsiText.padding( + snapshot.getUpdatedSnapshots().size() + " updated " + snapshot.getUpdatedSnapshots(), + 2 * TEST_PADDING)); + } + if (snapshot.getCreatedSnapshots().size() > 0) { + System.out.println(AnsiText.padding( + snapshot.getCreatedSnapshots().size() + " created " + snapshot.getCreatedSnapshots(), + 2 * TEST_PADDING)); + } + + updatedSnapshots += snapshot.getUpdatedSnapshots().size(); + createdSnapshots += snapshot.getCreatedSnapshots().size(); + + // if we have at least one skipped test, we can not + // determine if a snapshot is obsolete. + if (testSuite.hasSkippedTests() || testSuite.hasFailedTests()) { + System.out.println(AnsiText.padding( + "Obsolete snapshots can only be checked if all tests of a file are executed successful.", + 2 * TEST_PADDING)); + return; + } + + if (snapshot.getObsoleteSnapshots().size() > 0) { + System.out.println(AnsiColors.yellow(AnsiText.padding( + snapshot.getObsoleteSnapshots().size() + " obsolete " + snapshot.getObsoleteSnapshots(), + 2 * TEST_PADDING))); + } + + obsoleteSnapshots += snapshot.getObsoleteSnapshots().size(); + } @Override diff --git a/src/main/java/com/askimed/nf/test/core/ITestSuite.java b/src/main/java/com/askimed/nf/test/core/ITestSuite.java index e2334805..889a64d9 100644 --- a/src/main/java/com/askimed/nf/test/core/ITestSuite.java +++ b/src/main/java/com/askimed/nf/test/core/ITestSuite.java @@ -4,6 +4,7 @@ import java.util.List; import com.askimed.nf.test.config.Config; +import com.askimed.nf.test.lang.extensions.SnapshotFile; public interface ITestSuite extends ITaggable { @@ -22,5 +23,15 @@ public interface ITestSuite extends ITaggable { public String getDirectory(); public void configure(Config config); + + public boolean hasSkippedTests(); + + public void setFailedTests(boolean b); + + public boolean hasFailedTests(); + + public SnapshotFile getSnapshot(); + + public boolean hasSnapshotLoaded(); } \ No newline at end of file diff --git a/src/main/java/com/askimed/nf/test/core/TestExecutionEngine.java b/src/main/java/com/askimed/nf/test/core/TestExecutionEngine.java index d2f0a3c0..a8222921 100644 --- a/src/main/java/com/askimed/nf/test/core/TestExecutionEngine.java +++ b/src/main/java/com/askimed/nf/test/core/TestExecutionEngine.java @@ -7,6 +7,7 @@ import java.util.Vector; import com.askimed.nf.test.lang.TestSuiteBuilder; +import com.askimed.nf.test.lang.extensions.SnapshotFile; import com.askimed.nf.test.plugins.PluginManager; import com.askimed.nf.test.util.AnsiColors; import com.askimed.nf.test.util.AnsiText; @@ -35,6 +36,8 @@ public class TestExecutionEngine { private boolean updateSnapshot = false; + private boolean cleanSnapshot = false; + private String libDir = ""; private PluginManager pluginManager = null; @@ -75,6 +78,10 @@ public void setUpdateSnapshot(boolean updateSnapshot) { this.updateSnapshot = updateSnapshot; } + public void setCleanSnapshot(boolean cleanSnapshot) { + this.cleanSnapshot = cleanSnapshot; + } + public void setTagQuery(TagQuery tagQuery) { this.tagQuery = tagQuery; } @@ -199,6 +206,7 @@ public int execute() throws Throwable { result.setThrowable(e); result.setErrorReport(test.getErrorReport()); failed = true; + testSuite.setFailedTests(true); } test.cleanup(); @@ -207,6 +215,14 @@ public int execute() throws Throwable { } + // Remove obsolete snapshots when no test was skipped and no test failed. + if (cleanSnapshot && !testSuite.hasSkippedTests() && !testSuite.hasFailedTests() + && testSuite.hasSnapshotLoaded()) { + SnapshotFile snapshot = testSuite.getSnapshot(); + snapshot.removeObsoleteSnapshots(); + snapshot.save(); + } + listener.testSuiteExecutionFinished(testSuite); } diff --git a/src/main/java/com/askimed/nf/test/lang/WorkflowMeta.java b/src/main/java/com/askimed/nf/test/lang/WorkflowMeta.java index f59e5ded..7d3a5413 100644 --- a/src/main/java/com/askimed/nf/test/lang/WorkflowMeta.java +++ b/src/main/java/com/askimed/nf/test/lang/WorkflowMeta.java @@ -148,5 +148,10 @@ public void setName(String name) { public String getName() { return name; } + + @Override + public String toString() { + return name; + } } diff --git a/src/main/java/com/askimed/nf/test/lang/extensions/Snapshot.java b/src/main/java/com/askimed/nf/test/lang/extensions/Snapshot.java index 0a49d189..a1f14122 100644 --- a/src/main/java/com/askimed/nf/test/lang/extensions/Snapshot.java +++ b/src/main/java/com/askimed/nf/test/lang/extensions/Snapshot.java @@ -1,6 +1,6 @@ package com.askimed.nf.test.lang.extensions; -import java.util.Date; +import java.io.IOException; import com.askimed.nf.test.core.ITest; @@ -14,28 +14,29 @@ public class Snapshot { public Snapshot(Object actual, ITest test) { this.actual = actual; - this.file = SnapshotFile.loadByTestSuite(test.getTestSuite()); + this.file = test.getTestSuite().getSnapshot(); this.test = test; } - public boolean match() { + public boolean match() throws IOException { return match(test.getName()); } - public boolean match(String id) { + public boolean match(String id) throws IOException { SnapshotFileItem expected = file.getSnapshot(id); + //new snapshot --> create snapshot if (expected == null) { - file.updateSnapshot(id, actual); + file.createSnapshot(id, actual); file.save(); return true; } try { - return new SnapshotFileItem(new Date(), actual).equals(expected); + //compare actual snapshot with expected + return new SnapshotFileItem(actual).equals(expected); } catch (Exception e) { - // test failes + // test failes and flag set --> update snapshot if (test.isUpdateSnapshot()) { - // udpate snapshot file.updateSnapshot(id, actual); file.save(); return true; @@ -45,9 +46,9 @@ public boolean match(String id) { } } - + public void view() { - + } } diff --git a/src/main/java/com/askimed/nf/test/lang/extensions/SnapshotFile.java b/src/main/java/com/askimed/nf/test/lang/extensions/SnapshotFile.java index d568735e..ab571bbc 100644 --- a/src/main/java/com/askimed/nf/test/lang/extensions/SnapshotFile.java +++ b/src/main/java/com/askimed/nf/test/lang/extensions/SnapshotFile.java @@ -3,18 +3,15 @@ import java.io.File; import java.io.FileWriter; import java.io.IOException; -import java.nio.file.Path; -import java.security.NoSuchAlgorithmException; -import java.util.Date; import java.util.HashMap; -import java.util.List; +import java.util.HashSet; import java.util.Map; -import java.util.Vector; +import java.util.Set; import com.askimed.nf.test.core.ITestSuite; +import com.askimed.nf.test.lang.extensions.util.PathConverter; import groovy.json.JsonGenerator; -import groovy.json.JsonGenerator.Converter; import groovy.json.JsonOutput; import groovy.json.JsonSlurper; @@ -24,6 +21,14 @@ public class SnapshotFile { private Map snapshots = new HashMap(); + private Set activeSnapshots = new HashSet(); + + private Set createdSnapshots = new HashSet(); + + private Set updatedSnapshots = new HashSet(); + + private boolean removedSnapshots = false; + public static SnapshotFile loadByTestSuite(ITestSuite suite) { String filename = createFilename(suite); return new SnapshotFile(filename); @@ -47,39 +52,78 @@ public SnapshotFile(String filename) { Map> map = (Map>) jsonSlurper.parse(file); for (String id : map.keySet()) { Map object = map.get(id); - SnapshotFileItem item = new SnapshotFileItem(new Date(), object.get("content")); + String timestamp = object.get("timestamp").toString(); + Object content = object.get("content"); + SnapshotFileItem item = new SnapshotFileItem(timestamp, content); snapshots.put(id, item); } } public SnapshotFileItem getSnapshot(String id) { - return snapshots.get(id); + SnapshotFileItem snapshot = snapshots.get(id); + if (snapshot != null) { + activeSnapshots.add(id); + } + return snapshot; + } + + public void createSnapshot(String id, Object object) { + createdSnapshots.add(id); + activeSnapshots.add(id); + snapshots.put(id, new SnapshotFileItem(object)); } public void updateSnapshot(String id, Object object) { - snapshots.put(id, new SnapshotFileItem(new Date(), object)); + updatedSnapshots.add(id); + snapshots.put(id, new SnapshotFileItem(object)); + } + + public Set getCreatedSnapshots() { + return createdSnapshots; + } + + public Set getUpdatedSnapshots() { + return updatedSnapshots; + } + + public Set getActiveSnapshots() { + return activeSnapshots; + } + + public Set getObsoleteSnapshots() { + Set obsolete = new HashSet(snapshots.keySet()); + obsolete.removeAll(activeSnapshots); + return obsolete; + } + + public void removeObsoleteSnapshots() { + removeSnapshots(getObsoleteSnapshots()); + removedSnapshots = true; } - public void save() { + public boolean hasRemovedSnapsshots() { + return removedSnapshots; + } + + private void removeSnapshots(Set obsoleteSnapshots) { + for (String snapshot : obsoleteSnapshots) { + snapshots.remove(snapshot); + } + } + + public void save() throws IOException { JsonGenerator jsonGenerator = createJsonGenerator(); String json = jsonGenerator.toJson(snapshots); String prettyJson = JsonOutput.prettyPrint(json); File file = new File(filename); FileWriter writer; - try { - writer = new FileWriter(file); - writer.append(prettyJson); - writer.close(); - } catch (IOException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } - + writer = new FileWriter(file); + writer.append(prettyJson); + writer.close(); } protected static String createFilename(ITestSuite suite) { - // TODO: create subfolder snapshots? read from config? return suite.getFilename() + ".snap"; } @@ -89,58 +133,5 @@ public static JsonGenerator createJsonGenerator() { return jsonGenerator; } - static class PathConverter implements Converter { - - @Override - public boolean handles(Class type) { - return true; - } - - @Override - public Object convert(Object value, String key) { - Path path = null; - if (value instanceof Path) { - path = (Path) value; - if (!path.toFile().exists()) { - throw new RuntimeException("Path " + path.toString() + " not found."); - } - } else { - path = new File(value.toString()).toPath(); - - } - - if (path.toFile().exists()) { - try { - if (path.toFile().isFile()) { - return serializeFile(path); - } else { - return serializeDirectory(path); - } - // return path.getFileName() + ":base64," + FileUtil.encodeBase64(path); - } catch (Exception e) { - // TODO Auto-generated catch block - e.printStackTrace(); - return value; - } - } - return value; - } - - private String serializeFile(Path path) throws NoSuchAlgorithmException, IOException { - return path.getFileName() + ":md5," + PathExtension.getMd5(path); - } - - private List serializeDirectory(Path folder) throws NoSuchAlgorithmException, IOException { - List files = new Vector(); - for (Path subPath : PathExtension.list(folder)) { - if (subPath.toFile().isDirectory()) { - files.add(serializeDirectory(subPath)); - } else { - files.add(serializeFile(subPath)); - } - } - return files; - } - } } diff --git a/src/main/java/com/askimed/nf/test/lang/extensions/SnapshotFileItem.java b/src/main/java/com/askimed/nf/test/lang/extensions/SnapshotFileItem.java index f4f12f7a..9957b624 100644 --- a/src/main/java/com/askimed/nf/test/lang/extensions/SnapshotFileItem.java +++ b/src/main/java/com/askimed/nf/test/lang/extensions/SnapshotFileItem.java @@ -1,6 +1,7 @@ package com.askimed.nf.test.lang.extensions; -import java.util.Date; +import java.time.LocalDateTime; +import java.time.format.DateTimeFormatter; import groovy.json.JsonGenerator; import groovy.json.JsonOutput; @@ -9,18 +10,25 @@ public class SnapshotFileItem { private Object content; - private Date timestamp; + private String timestamp; - public SnapshotFileItem(Date timestamp, Object object) { - content = object; + public static DateTimeFormatter TIMESTAMP_FORMAT = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ssZ"); + + public SnapshotFileItem(Object content) { + this.timestamp = createTimestamp(); + this.content = content; + } + + public SnapshotFileItem(String timestamp, Object content) { this.timestamp = timestamp; + this.content = content; } public Object getContent() { return content; } - public Date getTimestamp() { + public String getTimestamp() { return timestamp; } @@ -45,6 +53,10 @@ public boolean equals(Object object) { } + protected String createTimestamp() { + return DateTimeFormatter.ISO_DATE_TIME.format(LocalDateTime.now()); + } + @Override public String toString() { JsonGenerator jsonGenerator = SnapshotFile.createJsonGenerator(); diff --git a/src/main/java/com/askimed/nf/test/lang/extensions/util/PathConverter.java b/src/main/java/com/askimed/nf/test/lang/extensions/util/PathConverter.java new file mode 100644 index 00000000..47d1d56f --- /dev/null +++ b/src/main/java/com/askimed/nf/test/lang/extensions/util/PathConverter.java @@ -0,0 +1,66 @@ +package com.askimed.nf.test.lang.extensions.util; + +import java.io.File; +import java.io.IOException; +import java.nio.file.Path; +import java.security.NoSuchAlgorithmException; +import java.util.List; +import java.util.Vector; + +import com.askimed.nf.test.lang.extensions.PathExtension; + +import groovy.json.JsonGenerator.Converter; + +public class PathConverter implements Converter { + + @Override + public boolean handles(Class type) { + return true; + } + + @Override + public Object convert(Object value, String key) { + Path path = null; + if (value instanceof Path) { + path = (Path) value; + if (!path.toFile().exists()) { + throw new RuntimeException("Path " + path.toString() + " not found."); + } + } else { + path = new File(value.toString()).toPath(); + + } + + if (path.toFile().exists()) { + try { + if (path.toFile().isFile()) { + return serializeFile(path); + } else { + return serializeDirectory(path); + } + // return path.getFileName() + ":base64," + FileUtil.encodeBase64(path); + } catch (Exception e) { + // TODO Auto-generated catch block + e.printStackTrace(); + return value; + } + } + return value; + } + + private String serializeFile(Path path) throws NoSuchAlgorithmException, IOException { + return path.getFileName() + ":md5," + PathExtension.getMd5(path); + } + + private List serializeDirectory(Path folder) throws NoSuchAlgorithmException, IOException { + List files = new Vector(); + for (Path subPath : PathExtension.list(folder)) { + if (subPath.toFile().isDirectory()) { + files.add(serializeDirectory(subPath)); + } else { + files.add(serializeFile(subPath)); + } + } + return files; + } +} \ No newline at end of file diff --git a/src/main/java/com/askimed/nf/test/lang/function/Function.java b/src/main/java/com/askimed/nf/test/lang/function/Function.java index 8b0a4f82..95cfed88 100644 --- a/src/main/java/com/askimed/nf/test/lang/function/Function.java +++ b/src/main/java/com/askimed/nf/test/lang/function/Function.java @@ -12,12 +12,6 @@ public class Function extends WorkflowMeta { private String mapping = ""; - private String name = "function"; - - public void setName(String name) { - this.name = name; - } - public void setMapping(String mapping) { this.mapping = mapping; } @@ -34,11 +28,6 @@ public void setResult(Object result) { this.result = result; } - @Override - public String toString() { - return name; - } - public void loadResult(File folder) { File file = new File(folder, "function.json"); @@ -46,7 +35,7 @@ public void loadResult(File folder) { JsonSlurper jsonSlurper = new JsonSlurper(); result = jsonSlurper.parse(file); } - + } - + } \ No newline at end of file diff --git a/src/main/java/com/askimed/nf/test/lang/function/FunctionContext.java b/src/main/java/com/askimed/nf/test/lang/function/FunctionContext.java index e3a80182..bad61ef3 100644 --- a/src/main/java/com/askimed/nf/test/lang/function/FunctionContext.java +++ b/src/main/java/com/askimed/nf/test/lang/function/FunctionContext.java @@ -14,7 +14,7 @@ public class FunctionContext extends TestContext { public FunctionContext(ITest test) { super(test); } - + public Function getFunction() { return function; } @@ -23,7 +23,10 @@ public void setFunction(Function function) { this.function = function; } - + public void setName(String name) { + function.setName(name); + } + public void function(Closure closure) { functionClosure = closure; } @@ -40,5 +43,5 @@ public void evaluateFunctionClosure() { } } - + } diff --git a/src/main/java/com/askimed/nf/test/lang/process/Process.java b/src/main/java/com/askimed/nf/test/lang/process/Process.java index b58a1826..e796c3d5 100644 --- a/src/main/java/com/askimed/nf/test/lang/process/Process.java +++ b/src/main/java/com/askimed/nf/test/lang/process/Process.java @@ -11,12 +11,6 @@ public class Process extends WorkflowMeta { private String mapping = ""; - private String name = "process"; - - public void setName(String name) { - this.name = name; - } - public void setMapping(String mapping) { this.mapping = mapping; } @@ -40,9 +34,4 @@ public void viewChannels() { out.view(); } - @Override - public String toString() { - return name; - } - } \ No newline at end of file diff --git a/src/test/java/com/askimed/nf/test/lang/FunctionTest.java b/src/test/java/com/askimed/nf/test/lang/FunctionTest.java index 5751e036..06fc609e 100644 --- a/src/test/java/com/askimed/nf/test/lang/FunctionTest.java +++ b/src/test/java/com/askimed/nf/test/lang/FunctionTest.java @@ -37,6 +37,15 @@ public void testScriptSucces() throws Exception { } + @Test + public void testScriptWithSnapshot() throws Exception { + + App app = new App(); + int exitCode = app.run(new String[] { "test", "test-data/function/default/functions.snapshot.nf.test" }); + assertEquals(0, exitCode); + + } + @Test public void testScriptWihtMultipleFunctions() throws Exception { @@ -45,15 +54,14 @@ public void testScriptWihtMultipleFunctions() throws Exception { assertEquals(0, exitCode); } - + @Test public void testGroovyScript() throws Exception { App app = new App(); - int exitCode = app.run(new String[] { "test", "test-data/function/utils/Utils.groovy.test" ,"--debug"}); + int exitCode = app.run(new String[] { "test", "test-data/function/utils/Utils.groovy.test", "--debug" }); assertEquals(0, exitCode); } - } diff --git a/test-data/function/default/functions.snapshot.nf.test b/test-data/function/default/functions.snapshot.nf.test new file mode 100644 index 00000000..8d5f73b5 --- /dev/null +++ b/test-data/function/default/functions.snapshot.nf.test @@ -0,0 +1,28 @@ +nextflow_function { + + name "Test Function Say Hello" + + script "test-data/function/default/functions.nf" + function "say_hello" + + test("Passing case") { + + when { + function { + """ + input[0] = "aaron" + """ + } + } + + then { + snapshot(function).match("forer lukas") + //assert function.success + //assert function.result == "Hello aaron" + //assert function.stdout.contains("Hello aaron") + //assert function.stderr.isEmpty() + } + + } + +} \ No newline at end of file diff --git a/test-data/function/default/functions.snapshot.nf.test.snap b/test-data/function/default/functions.snapshot.nf.test.snap new file mode 100644 index 00000000..17f2bd4b --- /dev/null +++ b/test-data/function/default/functions.snapshot.nf.test.snap @@ -0,0 +1,27 @@ +{ + "forer lukas": { + "content": [ + { + "stderr": [ + + ], + "errorReport": null, + "exitStatus": 0, + "failed": false, + "result": "Hello aaron", + "stdout": [ + "Hello aaron" + ], + "errorMessage": null, + "trace": { + "tasksFailed": 0, + "tasksCount": 0, + "tasksSucceeded": 0 + }, + "name": "say_hello", + "success": true + } + ], + "timestamp": "2023-08-26T15:20:15.069134" + } +} \ No newline at end of file