From a32347dd82c306e1073014b18cf243f3b53fd950 Mon Sep 17 00:00:00 2001
From: Eike Cochu <eike@cochu.com>
Date: Fri, 12 Feb 2016 22:59:39 +0100
Subject: [PATCH] added documentation

added some documentation
refactored some util classes
renamed databaseservice to mongoservice
---
 .../de/vipra/cmd/option/ClearCommand.java     |  14 +-
 .../de/vipra/cmd/option/ImportCommand.java    |  16 +-
 .../de/vipra/cmd/option/ModelingCommand.java  |  16 +-
 .../de/vipra/cmd/option/StatsCommand.java     |  14 +-
 .../java/de/vipra/cmd/option/TestCommand.java |   4 +-
 .../vipra/rest/resource/ArticleResource.java  |   6 +-
 .../de/vipra/rest/resource/TopicResource.java |  10 +-
 .../de/vipra/rest/resource/WordResource.java  |  10 +-
 .../src/main/java/de/vipra/util/Config.java   |   6 +-
 .../main/java/de/vipra/util/NestedMap.java    |  16 +-
 .../src/main/java/de/vipra/util/Timer.java    |  42 ++++-
 .../src/main/java/de/vipra/util/WordMap.java  |   6 +-
 ...DatabaseService.java => MongoService.java} |   8 +-
 .../java/de/vipra/util/service/Service.java   | 157 ++++++++++++++++++
 14 files changed, 261 insertions(+), 64 deletions(-)
 rename vipra-util/src/main/java/de/vipra/util/service/{DatabaseService.java => MongoService.java} (94%)

diff --git a/vipra-cmd/src/main/java/de/vipra/cmd/option/ClearCommand.java b/vipra-cmd/src/main/java/de/vipra/cmd/option/ClearCommand.java
index d79ddf1a..24333e55 100644
--- a/vipra-cmd/src/main/java/de/vipra/cmd/option/ClearCommand.java
+++ b/vipra-cmd/src/main/java/de/vipra/cmd/option/ClearCommand.java
@@ -15,7 +15,7 @@ import de.vipra.util.ESClient;
 import de.vipra.util.model.Article;
 import de.vipra.util.model.TopicFull;
 import de.vipra.util.model.Word;
-import de.vipra.util.service.DatabaseService;
+import de.vipra.util.service.MongoService;
 
 public class ClearCommand implements Command {
 
@@ -23,9 +23,9 @@ public class ClearCommand implements Command {
 
 	private boolean defaults;
 	private Config config;
-	private DatabaseService<Article, ObjectId> dbArticles;
-	private DatabaseService<TopicFull, ObjectId> dbTopics;
-	private DatabaseService<Word, String> dbWords;
+	private MongoService<Article, ObjectId> dbArticles;
+	private MongoService<TopicFull, ObjectId> dbTopics;
+	private MongoService<Word, String> dbWords;
 	private Client elasticClient;
 
 	public ClearCommand(boolean defaults) {
@@ -34,9 +34,9 @@ public class ClearCommand implements Command {
 
 	private void clear() throws Exception {
 		config = Config.getConfig();
-		dbArticles = DatabaseService.getDatabaseService(config, Article.class);
-		dbTopics = DatabaseService.getDatabaseService(config, TopicFull.class);
-		dbWords = DatabaseService.getDatabaseService(config, Word.class);
+		dbArticles = MongoService.getDatabaseService(config, Article.class);
+		dbTopics = MongoService.getDatabaseService(config, TopicFull.class);
+		dbWords = MongoService.getDatabaseService(config, Word.class);
 		elasticClient = ESClient.getClient(config);
 
 		log.info("clearing database");
diff --git a/vipra-cmd/src/main/java/de/vipra/cmd/option/ImportCommand.java b/vipra-cmd/src/main/java/de/vipra/cmd/option/ImportCommand.java
index 3050019c..cf02f052 100644
--- a/vipra-cmd/src/main/java/de/vipra/cmd/option/ImportCommand.java
+++ b/vipra-cmd/src/main/java/de/vipra/cmd/option/ImportCommand.java
@@ -27,16 +27,16 @@ import de.vipra.util.model.Article;
 import de.vipra.util.model.ArticleFull;
 import de.vipra.util.model.ArticleStats;
 import de.vipra.util.model.Word;
-import de.vipra.util.service.DatabaseService;
+import de.vipra.util.service.MongoService;
 
 public class ImportCommand implements Command {
 
 	public static class ArticleBuffer {
 
-		private DatabaseService<ArticleFull, ObjectId> dbArticles;
+		private MongoService<ArticleFull, ObjectId> dbArticles;
 		private List<ArticleFull> articles = new ArrayList<>(Constants.IMPORT_BUFFER_MAX);
 
-		public ArticleBuffer(DatabaseService<ArticleFull, ObjectId> dbArticles) {
+		public ArticleBuffer(MongoService<ArticleFull, ObjectId> dbArticles) {
 			this.dbArticles = dbArticles;
 		}
 
@@ -58,8 +58,8 @@ public class ImportCommand implements Command {
 	private ArrayList<File> files = new ArrayList<>();
 	private JSONParser parser = new JSONParser();
 	private Config config;
-	private DatabaseService<ArticleFull, ObjectId> dbArticles;
-	private DatabaseService<Word, String> dbWords;
+	private MongoService<ArticleFull, ObjectId> dbArticles;
+	private MongoService<Word, String> dbWords;
 	private Filebase filebase;
 	private Processor preprocessor;
 	private WordMap wordMap;
@@ -184,8 +184,8 @@ public class ImportCommand implements Command {
 	@Override
 	public void run() throws Exception {
 		config = Config.getConfig();
-		dbArticles = DatabaseService.getDatabaseService(config, ArticleFull.class);
-		dbWords = DatabaseService.getDatabaseService(config, Word.class);
+		dbArticles = MongoService.getDatabaseService(config, ArticleFull.class);
+		dbWords = MongoService.getDatabaseService(config, Word.class);
 		filebase = Filebase.getFilebase(config);
 		preprocessor = Processor.getProcessor(config);
 		wordMap = new WordMap(dbWords);
@@ -195,7 +195,7 @@ public class ImportCommand implements Command {
 		log.info("using preprocessor: " + preprocessor.getName());
 
 		Timer timer = new Timer();
-		timer.start();
+		timer.restart();
 
 		/*
 		 * import files into database and filebase
diff --git a/vipra-cmd/src/main/java/de/vipra/cmd/option/ModelingCommand.java b/vipra-cmd/src/main/java/de/vipra/cmd/option/ModelingCommand.java
index 26a179e8..8f0b79fa 100644
--- a/vipra-cmd/src/main/java/de/vipra/cmd/option/ModelingCommand.java
+++ b/vipra-cmd/src/main/java/de/vipra/cmd/option/ModelingCommand.java
@@ -31,16 +31,16 @@ import de.vipra.util.model.Topic;
 import de.vipra.util.model.TopicFull;
 import de.vipra.util.model.TopicRef;
 import de.vipra.util.model.Word;
-import de.vipra.util.service.DatabaseService;
+import de.vipra.util.service.MongoService;
 
 public class ModelingCommand implements Command {
 
 	public static final Logger log = LogManager.getLogger(ModelingCommand.class);
 
 	private Config config;
-	private DatabaseService<ArticleFull, ObjectId> dbArticles;
-	private DatabaseService<TopicFull, ObjectId> dbTopics;
-	private DatabaseService<Word, String> dbWords;
+	private MongoService<ArticleFull, ObjectId> dbArticles;
+	private MongoService<TopicFull, ObjectId> dbTopics;
+	private MongoService<Word, String> dbWords;
 	private Filebase filebase;
 	private WordMap wordMap;
 	private Analyzer analyzer;
@@ -50,9 +50,9 @@ public class ModelingCommand implements Command {
 	@Override
 	public void run() throws Exception {
 		config = Config.getConfig();
-		dbArticles = DatabaseService.getDatabaseService(config, ArticleFull.class);
-		dbTopics = DatabaseService.getDatabaseService(config, TopicFull.class);
-		dbWords = DatabaseService.getDatabaseService(config, Word.class);
+		dbArticles = MongoService.getDatabaseService(config, ArticleFull.class);
+		dbTopics = MongoService.getDatabaseService(config, TopicFull.class);
+		dbWords = MongoService.getDatabaseService(config, Word.class);
 		filebase = Filebase.getFilebase(config);
 		wordMap = new WordMap(dbWords);
 		analyzer = Analyzer.getAnalyzer(config, wordMap);
@@ -62,7 +62,7 @@ public class ModelingCommand implements Command {
 		log.info("using analyzer: " + analyzer.getName());
 
 		Timer timer = new Timer();
-		timer.start();
+		timer.restart();
 
 		/*
 		 * do topic modeling
diff --git a/vipra-cmd/src/main/java/de/vipra/cmd/option/StatsCommand.java b/vipra-cmd/src/main/java/de/vipra/cmd/option/StatsCommand.java
index 5202375e..31d7c3c5 100644
--- a/vipra-cmd/src/main/java/de/vipra/cmd/option/StatsCommand.java
+++ b/vipra-cmd/src/main/java/de/vipra/cmd/option/StatsCommand.java
@@ -8,16 +8,16 @@ import de.vipra.util.Config;
 import de.vipra.util.model.Article;
 import de.vipra.util.model.Topic;
 import de.vipra.util.model.Word;
-import de.vipra.util.service.DatabaseService;
+import de.vipra.util.service.MongoService;
 
 public class StatsCommand implements Command {
 
 	public static final Logger log = LogManager.getLogger(StatsCommand.class);
 
 	private Config config;
-	private DatabaseService<Article, ObjectId> dbArticles;
-	private DatabaseService<Topic, ObjectId> dbTopics;
-	private DatabaseService<Word, String> dbWords;
+	private MongoService<Article, ObjectId> dbArticles;
+	private MongoService<Topic, ObjectId> dbTopics;
+	private MongoService<Word, String> dbWords;
 
 	private void stats() {
 		log.info("# of articles: " + dbArticles.count());
@@ -28,9 +28,9 @@ public class StatsCommand implements Command {
 	@Override
 	public void run() throws Exception {
 		config = Config.getConfig();
-		dbArticles = DatabaseService.getDatabaseService(config, Article.class);
-		dbTopics = DatabaseService.getDatabaseService(config, Topic.class);
-		dbWords = DatabaseService.getDatabaseService(config, Word.class);
+		dbArticles = MongoService.getDatabaseService(config, Article.class);
+		dbTopics = MongoService.getDatabaseService(config, Topic.class);
+		dbWords = MongoService.getDatabaseService(config, Word.class);
 
 		stats();
 	}
diff --git a/vipra-cmd/src/main/java/de/vipra/cmd/option/TestCommand.java b/vipra-cmd/src/main/java/de/vipra/cmd/option/TestCommand.java
index dfc57e9a..96abc641 100644
--- a/vipra-cmd/src/main/java/de/vipra/cmd/option/TestCommand.java
+++ b/vipra-cmd/src/main/java/de/vipra/cmd/option/TestCommand.java
@@ -9,7 +9,7 @@ import org.elasticsearch.client.transport.TransportClient;
 import de.vipra.util.Config;
 import de.vipra.util.ESClient;
 import de.vipra.util.model.Article;
-import de.vipra.util.service.DatabaseService;
+import de.vipra.util.service.MongoService;
 
 public class TestCommand implements Command {
 
@@ -23,7 +23,7 @@ public class TestCommand implements Command {
 
 		// test if database is accessible
 		log.info("testing mongodb connection...");
-		DatabaseService<Article, ObjectId> dbArticles = DatabaseService.getDatabaseService(config, Article.class);
+		MongoService<Article, ObjectId> dbArticles = MongoService.getDatabaseService(config, Article.class);
 		dbArticles.count();
 
 		// test if elasticsearch is accessible
diff --git a/vipra-rest/src/main/java/de/vipra/rest/resource/ArticleResource.java b/vipra-rest/src/main/java/de/vipra/rest/resource/ArticleResource.java
index 8a02e335..59fb5f41 100644
--- a/vipra-rest/src/main/java/de/vipra/rest/resource/ArticleResource.java
+++ b/vipra-rest/src/main/java/de/vipra/rest/resource/ArticleResource.java
@@ -36,7 +36,7 @@ import de.vipra.util.StringUtils;
 import de.vipra.util.ex.ConfigException;
 import de.vipra.util.ex.DatabaseException;
 import de.vipra.util.model.ArticleFull;
-import de.vipra.util.service.DatabaseService;
+import de.vipra.util.service.MongoService;
 
 @Path("articles")
 public class ArticleResource {
@@ -44,11 +44,11 @@ public class ArticleResource {
 	@Context
 	UriInfo uri;
 
-	final DatabaseService<ArticleFull, ObjectId> dbArticles;
+	final MongoService<ArticleFull, ObjectId> dbArticles;
 
 	public ArticleResource(@Context ServletContext servletContext) throws ConfigException, IOException {
 		Config config = Config.getConfig();
-		dbArticles = DatabaseService.getDatabaseService(config, ArticleFull.class);
+		dbArticles = MongoService.getDatabaseService(config, ArticleFull.class);
 
 		CacheManager manager = (CacheManager) servletContext.getAttribute("cachemanager");
 		CacheAdapter<ObjectId, ArticleFull> cache = new CacheAdapter<>(manager, "articlecacle", ObjectId.class,
diff --git a/vipra-rest/src/main/java/de/vipra/rest/resource/TopicResource.java b/vipra-rest/src/main/java/de/vipra/rest/resource/TopicResource.java
index 21bf8c2c..7288668b 100644
--- a/vipra-rest/src/main/java/de/vipra/rest/resource/TopicResource.java
+++ b/vipra-rest/src/main/java/de/vipra/rest/resource/TopicResource.java
@@ -33,7 +33,7 @@ import de.vipra.util.ex.ConfigException;
 import de.vipra.util.ex.DatabaseException;
 import de.vipra.util.model.ArticleFull;
 import de.vipra.util.model.TopicFull;
-import de.vipra.util.service.DatabaseService;
+import de.vipra.util.service.MongoService;
 import de.vipra.util.service.Service.QueryBuilder;
 
 @Path("topics")
@@ -42,15 +42,15 @@ public class TopicResource {
 	@Context
 	UriInfo uri;
 
-	final DatabaseService<TopicFull, ObjectId> dbTopics;
-	final DatabaseService<ArticleFull, ObjectId> dbArticles;
+	final MongoService<TopicFull, ObjectId> dbTopics;
+	final MongoService<ArticleFull, ObjectId> dbArticles;
 
 	public static final Logger log = LogManager.getLogger(TopicResource.class);
 
 	public TopicResource(@Context ServletContext servletContext) throws ConfigException, IOException {
 		Config config = Config.getConfig();
-		dbTopics = DatabaseService.getDatabaseService(config, TopicFull.class);
-		dbArticles = DatabaseService.getDatabaseService(config, ArticleFull.class);
+		dbTopics = MongoService.getDatabaseService(config, TopicFull.class);
+		dbArticles = MongoService.getDatabaseService(config, ArticleFull.class);
 
 		CacheManager manager = (CacheManager) servletContext.getAttribute("cachemanager");
 		CacheAdapter<ObjectId, TopicFull> cache = new CacheAdapter<>(manager, "topiccache", ObjectId.class,
diff --git a/vipra-rest/src/main/java/de/vipra/rest/resource/WordResource.java b/vipra-rest/src/main/java/de/vipra/rest/resource/WordResource.java
index 46777bc0..f4997b69 100644
--- a/vipra-rest/src/main/java/de/vipra/rest/resource/WordResource.java
+++ b/vipra-rest/src/main/java/de/vipra/rest/resource/WordResource.java
@@ -28,7 +28,7 @@ import de.vipra.util.StringUtils;
 import de.vipra.util.ex.ConfigException;
 import de.vipra.util.model.TopicFull;
 import de.vipra.util.model.Word;
-import de.vipra.util.service.DatabaseService;
+import de.vipra.util.service.MongoService;
 import de.vipra.util.service.Service.QueryBuilder;
 
 @Path("words")
@@ -37,13 +37,13 @@ public class WordResource {
 	@Context
 	UriInfo uri;
 
-	final DatabaseService<Word, String> dbWords;
-	final DatabaseService<TopicFull, ObjectId> dbTopics;
+	final MongoService<Word, String> dbWords;
+	final MongoService<TopicFull, ObjectId> dbTopics;
 
 	public WordResource(@Context ServletContext servletContext) throws ConfigException, IOException {
 		Config config = Config.getConfig();
-		dbWords = DatabaseService.getDatabaseService(config, Word.class);
-		dbTopics = DatabaseService.getDatabaseService(config, TopicFull.class);
+		dbWords = MongoService.getDatabaseService(config, Word.class);
+		dbTopics = MongoService.getDatabaseService(config, TopicFull.class);
 
 		CacheManager manager = (CacheManager) servletContext.getAttribute("cachemanager");
 		CacheAdapter<String, Word> cache = new CacheAdapter<>(manager, "wordcache", String.class, Word.class);
diff --git a/vipra-util/src/main/java/de/vipra/util/Config.java b/vipra-util/src/main/java/de/vipra/util/Config.java
index a710af84..ba181570 100644
--- a/vipra-util/src/main/java/de/vipra/util/Config.java
+++ b/vipra-util/src/main/java/de/vipra/util/Config.java
@@ -22,7 +22,7 @@ import de.vipra.util.Constants.WindowResolution;
 import de.vipra.util.an.ConfigKey;
 import de.vipra.util.ex.ConfigException;
 import de.vipra.util.model.Model;
-import de.vipra.util.service.DatabaseService;
+import de.vipra.util.service.MongoService;
 
 /**
  * Vipra configuration
@@ -253,9 +253,9 @@ public class Config {
 	 * @return the database service
 	 * @throws ConfigException
 	 */
-	public <Type extends Model<IdType>, IdType> DatabaseService<Type, IdType> getDatabaseService(Class<Type> clazz)
+	public <Type extends Model<IdType>, IdType> MongoService<Type, IdType> getDatabaseService(Class<Type> clazz)
 			throws ConfigException {
-		return DatabaseService.getDatabaseService(this, clazz);
+		return MongoService.getDatabaseService(this, clazz);
 	}
 
 	/**
diff --git a/vipra-util/src/main/java/de/vipra/util/NestedMap.java b/vipra-util/src/main/java/de/vipra/util/NestedMap.java
index 183c0ff6..4c7856e8 100644
--- a/vipra-util/src/main/java/de/vipra/util/NestedMap.java
+++ b/vipra-util/src/main/java/de/vipra/util/NestedMap.java
@@ -2,16 +2,30 @@ package de.vipra.util;
 
 import java.util.HashMap;
 import java.util.Map;
+import java.util.regex.Pattern;
 
 import com.fasterxml.jackson.annotation.JsonCreator;
 import com.fasterxml.jackson.annotation.JsonValue;
 
+/**
+ * Nested map. This map is a rough implementation of JSON objects, featuring map
+ * nesting. Currently not supporting array notation. Can work with arbitrary
+ * field delimiters.
+ * 
+ * Default field delimiter is . (dot). Accessing fields is the same as in JSON:
+ * some.nested.object. Array notation is not implemented: some.nested[3].array
+ */
 public class NestedMap {
 
+	private String delimiter = Pattern.quote(".");
 	private Map<String, Object> map = new HashMap<>();
 
 	public NestedMap() {}
 
+	public NestedMap(String delimiter) {
+		this.delimiter = Pattern.quote(delimiter);
+	}
+
 	@JsonCreator
 	public NestedMap(Map<String, Object> map) {
 		this.map = map;
@@ -25,7 +39,7 @@ public class NestedMap {
 	@SuppressWarnings("unchecked")
 	public void put(String key, Object value) {
 		Map<String, Object> current = map;
-		String[] parts = key.split("\\.");
+		String[] parts = key.split(delimiter);
 		String name = parts.length > 0 ? parts[parts.length - 1] : key;
 
 		for (int i = 0; i < parts.length - 1; i++) {
diff --git a/vipra-util/src/main/java/de/vipra/util/Timer.java b/vipra-util/src/main/java/de/vipra/util/Timer.java
index bfaf35b8..fecf6572 100644
--- a/vipra-util/src/main/java/de/vipra/util/Timer.java
+++ b/vipra-util/src/main/java/de/vipra/util/Timer.java
@@ -4,34 +4,60 @@ import java.util.LinkedHashMap;
 import java.util.Map;
 import java.util.Map.Entry;
 
+/**
+ * Timer class for nano time measurements using {@link System#nanoTime()}.
+ * Advanced methods for creating multiple named sequential time frames (laps)
+ * and collective output
+ */
 public class Timer {
 
 	private long firstStart;
 	private long start;
 	private Map<String, Long> laps;
 
-	public long start() {
+	public Timer() {
+		restart();
+	}
+
+	/**
+	 * restart the timer (reset everything) and return the start time
+	 * 
+	 * @return start time
+	 */
+	public long restart() {
 		firstStart = start = System.nanoTime();
 		laps = new LinkedHashMap<>();
 		return start;
 	}
 
-	public long stop() {
+	/**
+	 * Return the current time since start or last lap, whichever is closer.
+	 * 
+	 * @return time since start or last lap
+	 */
+	public long current() {
 		return System.nanoTime() - start;
 	}
 
-	public long lap() {
+	/**
+	 * Create a named lap and reset the lap start time.
+	 * 
+	 * @param name
+	 *            Name of lap
+	 * @return lap time
+	 */
+	public long lap(String name) {
 		long lap = System.nanoTime() - start;
 		start = System.nanoTime();
-		return lap;
-	}
-
-	public long lap(String name) {
-		long lap = lap();
 		laps.put(name, lap);
 		return lap;
 	}
 
+	/**
+	 * Get total time since start or last reset, ignoring laps
+	 * 
+	 * @return total time
+	 */
 	public long total() {
 		return System.nanoTime() - firstStart;
 	}
diff --git a/vipra-util/src/main/java/de/vipra/util/WordMap.java b/vipra-util/src/main/java/de/vipra/util/WordMap.java
index 574f3ac0..1613e819 100644
--- a/vipra-util/src/main/java/de/vipra/util/WordMap.java
+++ b/vipra-util/src/main/java/de/vipra/util/WordMap.java
@@ -13,18 +13,18 @@ import org.slf4j.LoggerFactory;
 
 import de.vipra.util.ex.DatabaseException;
 import de.vipra.util.model.Word;
-import de.vipra.util.service.DatabaseService;
+import de.vipra.util.service.MongoService;
 
 public class WordMap {
 
 	public static final Logger log = LoggerFactory.getLogger(WordMap.class);
 
-	private final DatabaseService<Word, String> dbWords;
+	private final MongoService<Word, String> dbWords;
 	private final Map<String, Word> wordMap;
 	private final Set<Word> newWords;
 	private boolean createNow = false;
 
-	public WordMap(DatabaseService<Word, String> dbWords) {
+	public WordMap(MongoService<Word, String> dbWords) {
 		this.dbWords = dbWords;
 		this.wordMap = new HashMap<>();
 		this.newWords = new HashSet<>();
diff --git a/vipra-util/src/main/java/de/vipra/util/service/DatabaseService.java b/vipra-util/src/main/java/de/vipra/util/service/MongoService.java
similarity index 94%
rename from vipra-util/src/main/java/de/vipra/util/service/DatabaseService.java
rename to vipra-util/src/main/java/de/vipra/util/service/MongoService.java
index fdac1542..519d30ef 100644
--- a/vipra-util/src/main/java/de/vipra/util/service/DatabaseService.java
+++ b/vipra-util/src/main/java/de/vipra/util/service/MongoService.java
@@ -20,7 +20,7 @@ import de.vipra.util.ex.ConfigException;
 import de.vipra.util.ex.DatabaseException;
 import de.vipra.util.model.Model;
 
-public class DatabaseService<Type extends Model<IdType>, IdType> implements Service<Type, IdType, DatabaseException> {
+public class MongoService<Type extends Model<IdType>, IdType> implements Service<Type, IdType, DatabaseException> {
 
 	private final Datastore datastore;
 	private final Class<Type> clazz;
@@ -28,7 +28,7 @@ public class DatabaseService<Type extends Model<IdType>, IdType> implements Serv
 	private final String[] ignoredFieldsMulti;
 	private AbstractCache<IdType, Type> cache;
 
-	public DatabaseService(Mongo mongo, Class<Type> clazz) {
+	public MongoService(Mongo mongo, Class<Type> clazz) {
 		this.datastore = mongo.getDatastore();
 		this.clazz = clazz;
 
@@ -167,10 +167,10 @@ public class DatabaseService<Type extends Model<IdType>, IdType> implements Serv
 		this.cache = cache;
 	}
 
-	public static <Type extends Model<IdType>, IdType> DatabaseService<Type, IdType> getDatabaseService(Config config,
+	public static <Type extends Model<IdType>, IdType> MongoService<Type, IdType> getDatabaseService(Config config,
 			Class<Type> clazz) throws ConfigException {
 		Mongo mongo = config.getMongo();
-		return new DatabaseService<Type, IdType>(mongo, clazz);
+		return new MongoService<Type, IdType>(mongo, clazz);
 	}
 
 	private String[] setMinus(String[] a, String[] b) {
diff --git a/vipra-util/src/main/java/de/vipra/util/service/Service.java b/vipra-util/src/main/java/de/vipra/util/service/Service.java
index 16b40b15..d83fe03e 100644
--- a/vipra-util/src/main/java/de/vipra/util/service/Service.java
+++ b/vipra-util/src/main/java/de/vipra/util/service/Service.java
@@ -7,36 +7,138 @@ import de.vipra.util.AbstractCache;
 import de.vipra.util.Pair;
 import de.vipra.util.model.Model;
 
+/**
+ * Generic service interface, implemented by various database services to
+ * support multiple database engines.
+ *
+ * @param <Type>
+ *            Model type that is returned by service functions
+ * @param <IdType>
+ *            Id type that is used to identify models in the database
+ * @param <E>
+ *            Type of exception
+ */
 public interface Service<Type extends Model<IdType>, IdType, E extends Exception> {
 
+	/**
+	 * Returns a single entity from the database or null
+	 * 
+	 * @param id
+	 *            id of the entity
+	 * @param fields
+	 *            fields to be returned from the database, if supported
+	 * @return retrieved entity or null
+	 * @throws E
+	 */
 	Type getSingle(IdType id, String... fields) throws E;
 
+	/**
+	 * @see {@link Service#getMultiple(QueryBuilder)}
+	 */
 	List<Type> getMultiple(Integer skip, Integer limit, String sortBy, String... fields) throws E;
 
+	/**
+	 * @see {@link Service#getMultiple(QueryBuilder)}
+	 */
 	List<Type> getMultiple(Integer skip, Integer limit, String sortBy, Pair<String, Object> criteria, String... fields)
 			throws E;
 
+	/**
+	 * @see {@link Service#getMultiple(QueryBuilder)}
+	 */
 	List<Type> getMultiple(Integer skip, Integer limit, String sortBy, Pair<String, Object> criteria,
 			boolean noDefaultIgnore, String... fields) throws E;
 
+	/**
+	 * Returns multiple entities from the database.
+	 * 
+	 * @param builder
+	 *            query builder
+	 * @return found entities
+	 * @throws E
+	 * @see {@link QueryBuilder}
+	 */
 	List<Type> getMultiple(QueryBuilder builder) throws E;
 
+	/**
+	 * Return all entities.
+	 * 
+	 * @param fields
+	 *            fields to be returned
+	 * @return all entities
+	 * @throws E
+	 */
 	List<Type> getAll(String... fields) throws E;
 
+	/**
+	 * Create a single entity in the database
+	 * 
+	 * @param t
+	 *            Entity to be created
+	 * @return Created entity, with inserted id if supported
+	 * @throws E
+	 */
 	Type createSingle(Type t) throws E;
 
+	/**
+	 * Create multiple entities in the database
+	 * 
+	 * @param t
+	 *            Entities to be created
+	 * @return Created entities, with inserted ids if supported
+	 * @throws E
+	 */
 	List<Type> createMultiple(Iterable<Type> t) throws E;
 
+	/**
+	 * Deletes a single entity from the database
+	 * 
+	 * @param id
+	 *            id of entity to be deleted
+	 * @return number of deleted entities
+	 * @throws E
+	 */
 	long deleteSingle(IdType id) throws E;
 
+	/**
+	 * Update a single entity in the database
+	 * 
+	 * @param t
+	 *            Entity to be updated
+	 * @throws E
+	 */
 	void updateSingle(Type t) throws E;
 
+	/**
+	 * Drop all entities from the database
+	 * 
+	 * @throws E
+	 */
 	void drop() throws E;
 
+	/**
+	 * Count entities in the database
+	 * 
+	 * @return number of entities in the database
+	 * @throws E
+	 */
 	long count() throws E;
 
+	/**
+	 * Enables caching on entities
+	 * 
+	 * @param cache
+	 *            cache to be used
+	 * @see {@link AbstractCache}
+	 */
 	void withCache(AbstractCache<IdType, Type> cache);
 
+	/**
+	 * QueryBuilder instances are used to create complex queries for use with
+	 * the getMultiple method
+	 * 
+	 * @see {@link Service#getMultiple(QueryBuilder)}
+	 */
 	public static class QueryBuilder {
 
 		private Integer skip;
@@ -53,30 +155,67 @@ public interface Service<Type extends Model<IdType>, IdType, E extends Exception
 			return new QueryBuilder();
 		}
 
+		/**
+		 * Skip n entries
+		 * 
+		 * @param skip
+		 *            entries to skip
+		 * @return QueryBuilder instance
+		 */
 		public QueryBuilder skip(Integer skip) {
 			if (skip == null || skip >= 0)
 				this.skip = skip;
 			return this;
 		}
 
+		/**
+		 * Limit return size.
+		 * 
+		 * @param limit
+		 *            maximum return size
+		 * @return QueryBuilder instance
+		 */
 		public QueryBuilder limit(Integer limit) {
 			if (limit == null || limit >= 0)
 				this.limit = limit;
 			return this;
 		}
 
+		/**
+		 * Sort result by field
+		 * 
+		 * @param sortBy
+		 *            field to sort by.
+		 * @return QueryBuilder instance
+		 */
 		public QueryBuilder sortBy(String sortBy) {
 			if (sortBy == null || !sortBy.isEmpty())
 				this.sortBy = sortBy;
 			return this;
 		}
 
+		/**
+		 * Criteria used for filtering by field
+		 * 
+		 * @param field
+		 *            field to compare
+		 * @param value
+		 *            value to compare to
+		 * @return QueryBuilder instance
+		 */
 		public QueryBuilder criteria(String field, Object value) {
 			if (field != null && value != null && !field.isEmpty())
 				criteria(Pair.pair(field, value));
 			return this;
 		}
 
+		/**
+		 * Criteria used for filtering by field
+		 * 
+		 * @param pair
+		 *            field value pair to compare
+		 * @return QueryBuilder instance
+		 */
 		public QueryBuilder criteria(Pair<String, Object> pair) {
 			if (pair != null) {
 				if (criteria == null) {
@@ -87,12 +226,30 @@ public interface Service<Type extends Model<IdType>, IdType, E extends Exception
 			return this;
 		}
 
+		/**
+		 * Fields to return. Set include to false to exclude. Cannot be applied
+		 * multiple times, previous calls will be overwritten by later calls.
+		 * 
+		 * @param include
+		 *            true to include, false to exclude
+		 * @param strings
+		 *            fields to in/exclude
+		 * @return QueryBuilder instance
+		 */
 		public QueryBuilder fields(boolean include, String... strings) {
 			this.include = include;
 			this.fields = strings;
 			return this;
 		}
 
+		/**
+		 * Whether to use default ignoring fields or not. Some fields are
+		 * ignored by default, as per defined in the models.
+		 * 
+		 * @param defaultIgnore
+		 *            true to use default ignoring
+		 * @return QueryBuilder instance
+		 */
 		public QueryBuilder defaultIgnore(boolean defaultIgnore) {
 			this.defaultIgnore = defaultIgnore;
 			return this;
-- 
GitLab