diff --git a/mvn-debug b/mvn-debug new file mode 100755 index 000000000..066900f60 --- /dev/null +++ b/mvn-debug @@ -0,0 +1,2 @@ +export MAVEN_OPTS="-Xdebug -Xnoagent -Djava.compiler=NONE -Xrunjdwp:transport=dt_socket,server=y,suspend=y,address=8000" +mvn $@ diff --git a/src/main/java/org/owasp/webgoat/plugins/PluginExtractor.java b/src/main/java/org/owasp/webgoat/plugins/PluginExtractor.java index a9a2f1043..89723304f 100644 --- a/src/main/java/org/owasp/webgoat/plugins/PluginExtractor.java +++ b/src/main/java/org/owasp/webgoat/plugins/PluginExtractor.java @@ -49,8 +49,8 @@ public class PluginExtractor { return FileVisitResult.CONTINUE; } }); - } catch (IOException io) { - new Plugin.PluginLoadingFailure(format("Unable to extract: %s", pluginArchive.getFileName()), io); + } catch (Exception e) { + new Plugin.PluginLoadingFailure(format("Unable to extract: %s", pluginArchive.getFileName()), e); } } @@ -62,7 +62,7 @@ public class PluginExtractor { return this.files; } - private FileSystem createZipFileSystem() throws IOException { + private FileSystem createZipFileSystem() throws Exception { final URI uri = URI.create("jar:file:" + pluginArchive.toUri().getPath()); return FileSystems.newFileSystem(uri, new HashMap()); } diff --git a/src/main/java/org/owasp/webgoat/plugins/PluginFileUtils.java b/src/main/java/org/owasp/webgoat/plugins/PluginFileUtils.java index c0390539c..758119f0e 100644 --- a/src/main/java/org/owasp/webgoat/plugins/PluginFileUtils.java +++ b/src/main/java/org/owasp/webgoat/plugins/PluginFileUtils.java @@ -2,8 +2,11 @@ package org.owasp.webgoat.plugins; import java.io.IOException; +import java.nio.file.DirectoryStream; import java.nio.file.Files; import java.nio.file.Path; +import java.util.ArrayList; +import java.util.List; public class PluginFileUtils { @@ -27,5 +30,17 @@ public class PluginFileUtils { } return p; } + + public static List getFilesInDirectory( Path directory) throws IOException + { + List files = new ArrayList<>(); + DirectoryStream dirStream; + dirStream = Files.newDirectoryStream(directory); + for (Path entry : dirStream) { + files.add(entry); + } + dirStream.close(); + return files; + } } diff --git a/src/main/java/org/owasp/webgoat/plugins/PluginsLoader.java b/src/main/java/org/owasp/webgoat/plugins/PluginsLoader.java index 87ffc3669..6201f6542 100644 --- a/src/main/java/org/owasp/webgoat/plugins/PluginsLoader.java +++ b/src/main/java/org/owasp/webgoat/plugins/PluginsLoader.java @@ -14,7 +14,8 @@ import java.util.List; public class PluginsLoader implements Runnable { - private final Logger logger = LoggerFactory.getLogger(this.getClass()); + protected static final String WEBGOAT_PLUGIN_EXTENSION = "jar"; + private final Logger logger = LoggerFactory.getLogger(this.getClass()); private final Path pluginSource; private Path pluginTarget; @@ -31,14 +32,16 @@ public class PluginsLoader implements Runnable { @Override public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException { try { - PluginFileUtils.createDirsIfNotExists(pluginTarget); - PluginExtractor extractor = new PluginExtractor(file); - extractor.extract(pluginTarget); - Plugin plugin = new Plugin(pluginTarget); - plugin.loadClasses(extractor.getClasses()); - plugin.loadFiles(extractor.getFiles(), reload); - plugin.rewritePaths(pluginTarget); - plugins.add(plugin); + if (PluginFileUtils.fileEndsWith(file, WEBGOAT_PLUGIN_EXTENSION)) { + PluginFileUtils.createDirsIfNotExists(pluginTarget); + PluginExtractor extractor = new PluginExtractor(file); + extractor.extract(pluginTarget); + Plugin plugin = new Plugin(pluginTarget); + plugin.loadClasses(extractor.getClasses()); + plugin.loadFiles(extractor.getFiles(), reload); + plugin.rewritePaths(pluginTarget); + plugins.add(plugin); + } } catch (Plugin.PluginLoadingFailure e) { logger.error("Unable to load plugin, continue loading others..."); } diff --git a/src/main/java/org/owasp/webgoat/session/Course.java b/src/main/java/org/owasp/webgoat/session/Course.java index 6f4abd4e5..24a06a9d2 100644 --- a/src/main/java/org/owasp/webgoat/session/Course.java +++ b/src/main/java/org/owasp/webgoat/session/Course.java @@ -4,11 +4,13 @@ import org.owasp.webgoat.HammerHead; import org.owasp.webgoat.lessons.AbstractLesson; import org.owasp.webgoat.lessons.Category; import org.owasp.webgoat.plugins.Plugin; +import org.owasp.webgoat.plugins.PluginFileUtils; import org.owasp.webgoat.plugins.PluginsLoader; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import javax.servlet.ServletContext; + import java.io.File; import java.io.IOException; import java.nio.file.Path; @@ -175,7 +177,7 @@ public class Course { List roles = new ArrayList(); roles.add(AbstractLesson.USER_ROLE); // Category 0 is the admin function. We want the first real category - // to be returned. This is noramally the General category and the Http Basics lesson + // to be returned. This is normally the General category and the Http Basics lesson return ((AbstractLesson) getLessons((Category) getCategories().get(0), roles).get(0)); } @@ -281,7 +283,7 @@ public class Course { return null; } - private void loadLessionFromPlugin(ServletContext context) { + private void loadLessonFromPlugin(ServletContext context) { context.getContextPath(); logger.debug("Loading plugins into cache"); String pluginPath = context.getRealPath("plugin_lessons"); @@ -290,8 +292,18 @@ public class Course { logger.error("Plugins directory {} not found", pluginPath); return; } + + // Do a one time load of the container properties + String containerPath = context.getRealPath("container//i18n"); + Plugin theContainer = new Plugin(Paths.get(targetPath)); + try { + theContainer.loadFiles(PluginFileUtils.getFilesInDirectory(Paths.get(containerPath)), false); + } catch (IOException io) { + logger.error("Error loading container properties: ", io); + } + Path pluginDirectory = Paths.get(pluginPath); - List plugins = new PluginsLoader(Paths.get(pluginPath), Paths.get(targetPath)).loadPlugins(false); + List plugins = new PluginsLoader(Paths.get(pluginPath), Paths.get(targetPath)).loadPlugins(true); for (Plugin plugin : plugins) { try { Class c = plugin.getLesson(); @@ -326,7 +338,7 @@ public class Course { public void loadCourses(WebgoatContext webgoatContext, ServletContext context, String path) { logger.info("Loading courses: " + path); this.webgoatContext = webgoatContext; - loadLessionFromPlugin(context); + loadLessonFromPlugin(context); } } diff --git a/src/main/webapp/container/i18n/WebGoatLabels.properties b/src/main/webapp/container/i18n/WebGoatLabels.properties new file mode 100644 index 000000000..1f622dd2f --- /dev/null +++ b/src/main/webapp/container/i18n/WebGoatLabels.properties @@ -0,0 +1,7 @@ +#General +LessonCompleted=Congratulations. You have successfully completed this lesson. +RestartLesson=Restart this Lesson +SolutionVideos=Solution Videos +ErrorGenerating=Error generating +InvalidData=Invalid Data +Go!=Go! diff --git a/src/main/webapp/container/i18n/WebGoatLabels_de.properties b/src/main/webapp/container/i18n/WebGoatLabels_de.properties new file mode 100644 index 000000000..ea2065e0c --- /dev/null +++ b/src/main/webapp/container/i18n/WebGoatLabels_de.properties @@ -0,0 +1,7 @@ +#General +LessonCompleted=Herzlichen Gl\u00fcckwunsch! Sie haben diese Lektion erfolgreich abgeschlossen. +RestartLesson=Lektion neu beginnen +SolutionVideos=L\u00f6sungsvideos +ErrorGenerating=Fehler beim Generieren von +InvalidData=Ung\u00fcltige Daten +Go!=Los gehts! diff --git a/src/main/webapp/container/i18n/WebGoatLabels_fr.properties b/src/main/webapp/container/i18n/WebGoatLabels_fr.properties new file mode 100644 index 000000000..ebc86bb21 --- /dev/null +++ b/src/main/webapp/container/i18n/WebGoatLabels_fr.properties @@ -0,0 +1,7 @@ +#General +LessonCompleted=F\u00e9licitations. Vous avez termin\u00e9 cette le\u00e7on avec succ\u00e9s. +RestartLesson=Recommencer cette le\u00e7on +SolutionVideos=Solution vid\u00e9os +ErrorGenerating=Error generating +InvalidData=Donn\u00e9e invalide +Go!=Go! diff --git a/src/main/webapp/container/i18n/WebGoatLabels_ru.properties b/src/main/webapp/container/i18n/WebGoatLabels_ru.properties new file mode 100644 index 000000000..0c3b80ca0 --- /dev/null +++ b/src/main/webapp/container/i18n/WebGoatLabels_ru.properties @@ -0,0 +1,7 @@ +#General +LessonCompleted=\u041f\u043e\u0437\u0434\u0440\u0430\u0432\u043b\u044f\u044e. \u0412\u044b \u043f\u043e\u043b\u043d\u043e\u0441\u0442\u044c\u044e \u043f\u0440\u043e\u0448\u043b\u0438 \u0434\u0430\u043d\u043d\u044b\u0439 \u0443\u0440\u043e\u043a. +RestartLesson=\u041d\u0430\u0447\u0430\u043b\u044c \u0441\u043d\u0430\u0447\u0430\u043b\u0430 +SolutionVideos=\u0412\u0438\u0434\u0435\u043e \u0441 \u0440\u0435\u0448\u0435\u043d\u0438\u0435\u043c +ErrorGenerating=\u041f\u0440\u043e\u0438\u0437\u043e\u0448\u043b\u0430 \u043e\u0448\u0438\u0431\u043a\u0430 +InvalidData=\u041d\u0435\u0432\u0435\u0440\u043d\u044b\u0435 \u0434\u0430\u043d\u043d\u044b\u0435 +Go!=\u0412\u043f\u0435\u0440\u0451\u0434! diff --git a/src/main/webapp/plugin_lessons/ReadMe.txt b/src/main/webapp/plugin_lessons/ReadMe.txt new file mode 100644 index 000000000..101910ac2 --- /dev/null +++ b/src/main/webapp/plugin_lessons/ReadMe.txt @@ -0,0 +1 @@ +Lesson plugins stored under this directory. \ No newline at end of file diff --git a/src/main/webapp/plugin_lessons/SqlStringInjection-1.0.jar b/src/main/webapp/plugin_lessons/SqlStringInjection-1.0.jar index d032bb12c..707d626f9 100644 Binary files a/src/main/webapp/plugin_lessons/SqlStringInjection-1.0.jar and b/src/main/webapp/plugin_lessons/SqlStringInjection-1.0.jar differ