//Dstl (c) Crown Copyright 2017
package uk.gov.dstl.baleen.resources.gazetteer;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.apache.uima.resource.Resource;
import org.bson.Document;
import org.bson.types.ObjectId;
import com.mongodb.client.MongoCollection;
import uk.gov.dstl.baleen.exceptions.BaleenException;
import uk.gov.dstl.baleen.exceptions.InvalidParameterException;
import uk.gov.dstl.baleen.resources.SharedMongoResource;
/**
* Connect to MongoDB and use as the backend for a Gazetteer
*
*
*/
public class MongoGazetteer extends AbstractMultiMapGazetteer<ObjectId> {
public static final String CONFIG_COLLECTION = "collection";
public static final String CONFIG_VALUE_FIELD = "valueField";
public static final String DEFAULT_COLLECTION = "gazetteer";
public static final String DEFAULT_VALUE_FIELD = "value";
private MongoCollection<Document> coll;
private String valueField;
/**
* Configure a new instance of MongoGazetteer. The following config parameters are expected/allowed:
* <ul>
* <li><b>collection</b> - The collection containing the gazetteer; defaults to gazetteer</li>
* <li><b>valueField</b> - The field containing the gazetteer values; defaults to value</li>
* </ul>
*
* @param connection A SharedMongoResource object to use to connect to Mongo
* @param config A map of additional configuration options
*
* @throws InvalidParameterException if the passed connection parameter is not a SharedMongoResource
*/
@Override
public void init(Resource connection, Map<String, Object> config) throws BaleenException{
SharedMongoResource mongo;
try{
mongo = (SharedMongoResource) connection;
}catch(ClassCastException cce){
throw new InvalidParameterException("Unable to cast connection parameter to SharedMongoResource", cce);
}
valueField = DEFAULT_VALUE_FIELD;
if(config.containsKey(CONFIG_VALUE_FIELD)){
valueField = config.get(CONFIG_VALUE_FIELD).toString();
}
String collection = DEFAULT_COLLECTION;
if(config.containsKey(CONFIG_COLLECTION)){
collection = config.get(CONFIG_COLLECTION).toString();
}
coll = mongo.getDB().getCollection(collection);
super.init(connection, config);
}
@Override
public Map<String, Object> getAdditionalData(String key) {
ObjectId id = getId(key);
if(id == null){
return Collections.emptyMap();
}
Document doc = coll.find(new Document("_id", id)).projection(new Document(valueField, 0).append("_id", 0)).first();
if(doc == null){
return Collections.emptyMap();
}
Map<String, Object> ret = new HashMap<>();
for(String mongoKey : doc.keySet()){
Object val = doc.get(mongoKey);
ret.put(mongoKey, val);
}
return ret;
}
@Override
public void destroy() {
coll = null;
super.destroy();
}
@SuppressWarnings("unchecked")
@Override
public void reloadValues(){
reset();
for(Document doc : coll.find()){
ObjectId id = (ObjectId) doc.get("_id");
Object val = doc.get(valueField);
if(val instanceof String){
String s = (String) val;
addTerm(id, s);
}else if(val instanceof List){
for(String s : (List<String>)val){
addTerm(id, s);
}
}
}
}
}