com.esri.geoevent.solutions.processor.eventjoiner.EventJoinerProcessor.java Source code

Java tutorial

Introduction

Here is the source code for com.esri.geoevent.solutions.processor.eventjoiner.EventJoinerProcessor.java

Source

package com.esri.geoevent.solutions.processor.eventjoiner;

/*
 * #%L
 * FieldGrouperProcessor.java - fieldgrouper - Esri - 2013
 * org.codehaus.mojo-license-maven-plugin-1.5
 * $Id: update-file-header-config.apt.vm 17764 2012-12-12 10:22:04Z tchemit $
 * $HeadURL: https://svn.codehaus.org/mojo/tags/license-maven-plugin-1.5/src/site/apt/examples/update-file-header-config.apt.vm $
 * %%
 * Copyright (C) 2013 - 2014 Esri
 * %%
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 * 
 *      http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 * #L%
 */

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Set;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import com.esri.ges.core.ConfigurationException;
import com.esri.ges.core.component.ComponentException;
import com.esri.ges.core.geoevent.DefaultFieldDefinition;
import com.esri.ges.core.geoevent.DefaultGeoEventDefinition;
import com.esri.ges.core.geoevent.FieldDefinition;
import com.esri.ges.core.geoevent.FieldException;
import com.esri.ges.core.geoevent.FieldGroup;
import com.esri.ges.core.geoevent.FieldType;
import com.esri.ges.core.geoevent.GeoEvent;
import com.esri.ges.core.geoevent.GeoEventDefinition;
import com.esri.ges.core.geoevent.GeoEventPropertyName;
import com.esri.ges.manager.geoeventdefinition.GeoEventDefinitionManager;
import com.esri.ges.manager.geoeventdefinition.GeoEventDefinitionManagerException;
import com.esri.ges.messaging.GeoEventCreator;
import com.esri.ges.messaging.Messaging;
import com.esri.ges.messaging.MessagingException;
import com.esri.ges.processor.GeoEventProcessorBase;
import com.esri.ges.processor.GeoEventProcessorDefinition;

public class EventJoinerProcessor extends GeoEventProcessorBase {
    Messaging messaging;
    GeoEventDefinitionManager manager;
    Map<String, TrackRecord> recordCache;
    private static final Log LOG = LogFactory.getLog(EventJoinerProcessor.class);
    private String indefs;
    private String joinfield;
    private String outdefname;
    private List<String> defList;
    private Map<String, FieldItem> fldMgr;
    private final Double THRESHOLD_MILLISEC = 100000.0;
    private Boolean createNewDef;
    private GeoEventDefinition outDef = null;

    class TrackRecord {
        String id;
        List<HashMap<String, GeoEvent>> records = new ArrayList<HashMap<String, GeoEvent>>();

        public void setId(String id) {
            this.id = id;
        }
    }

    class FieldItem {
        String id;
        Integer count = 0;
        FieldType type;
        ArrayList<String> tags = new ArrayList<String>();

        public String getId() {
            return id;
        }

        public void setId(String id) {
            this.id = id;
        }

        public FieldType getType() {
            return type;
        }

        public void setType(FieldType type) {
            this.type = type;
        }

        public void appendTags(List<String> inTags) {

            for (String t : inTags) {
                if (!tags.contains(t)) {
                    tags.add(t);
                }
            }
        }

        public ArrayList<String> getTags() {
            return tags;
        }

        public Integer getCount() {
            return count;
        }

        public void advance() {
            ++count;
        }

    }

    public EventJoinerProcessor(GeoEventProcessorDefinition definition) throws ComponentException {
        super(definition);

    }

    public void setGeoEventDefinitionManager(GeoEventDefinitionManager gedm) {
        manager = gedm;
    }

    public void setMessaging(Messaging m) {
        messaging = m;
    }

    @Override
    public synchronized void afterPropertiesSet() {
        indefs = properties.get("indefs").getValueAsString();
        String[] defs = indefs.split(",", 0);
        defList = Arrays.asList(defs);
        outdefname = properties.get("outdef").getValueAsString();
        joinfield = properties.get("join").getValueAsString();
        if (fldMgr != null) {
            fldMgr.clear();
            fldMgr = null;
        }
        if (recordCache != null) {
            recordCache.clear();
            recordCache = null;
        }

        createNewDef = true;
    }

    @Override
    public void shutdown() {
        if (fldMgr != null) {
            fldMgr.clear();
            fldMgr = null;
        }
        if (recordCache != null) {
            recordCache.clear();
            recordCache = null;
        }

        createNewDef = true;
        super.shutdown();
    }

    public GeoEvent process(GeoEvent evt) throws Exception {
        try {
            if (recordCache == null)
                recordCache = new HashMap<String, TrackRecord>();
            String curDefName = evt.getGeoEventDefinition().getName();

            if (!defList.contains(curDefName))
                return null;
            String uid = evt.getField(joinfield).toString();
            if (!recordCache.containsKey(uid)) {
                TrackRecord tr = new TrackRecord();
                tr.setId(uid);
                HashMap<String, GeoEvent> joinEvents = new HashMap<String, GeoEvent>();
                joinEvents.put(curDefName, evt);
                tr.records.add(joinEvents);
                recordCache.put(uid, tr);
            } else {
                TrackRecord tr = recordCache.get(uid);
                Boolean exitLoop = false;
                while (!exitLoop) {
                    for (HashMap<String, GeoEvent> rec : tr.records) {
                        if (!rec.containsKey(curDefName)) {
                            rec.put(curDefName, evt);
                            if (rec.size() == defList.size()) {
                                if (createNewDef) {
                                    ConstructGeoEventDef(rec);
                                    createNewDef = false;
                                }
                                return CreateGeoEvent(rec);

                            }
                            exitLoop = true;
                        }

                    }
                    exitLoop = true;

                }
                HashMap<String, GeoEvent> joinEvents = new HashMap<String, GeoEvent>();
                joinEvents.put(curDefName, evt);
                tr.records.add(joinEvents);
            }
            return null;
        } catch (Exception e) {
            LOG.error(e.getMessage());
            throw (e);
        }
    }

    private void ConstructGeoEventDef(HashMap<String, GeoEvent> rec) throws Exception {
        try {
            fldMgr = new HashMap<String, FieldItem>();
            Set<String> keys = rec.keySet();
            Iterator<String> it = keys.iterator();
            while (it.hasNext()) {
                String key = it.next();
                GeoEvent evt = rec.get(key);
                List<FieldDefinition> fldDefs = evt.getGeoEventDefinition().getFieldDefinitions();
                for (FieldDefinition fldDef : fldDefs) {
                    String fldName = fldDef.getName();
                    FieldType type = fldDef.getType();
                    if (fldMgr.containsKey(fldName)) {
                        FieldItem item = fldMgr.get(fldName);
                        if (!fldDef.getTags().isEmpty())
                            item.appendTags(fldDef.getTags());
                        item.advance();
                    } else {
                        FieldItem item = new FieldItem();
                        item.setId(fldName);
                        item.setType(type);
                        if (!fldDef.getTags().isEmpty())
                            item.appendTags(fldDef.getTags());
                        item.advance();
                        fldMgr.put(fldName, item);
                    }
                }
            }
            Set<String> fldKeys = fldMgr.keySet();
            Iterator<String> fldIt = fldKeys.iterator();
            List<FieldDefinition> mergedFldDef = new ArrayList<FieldDefinition>();
            while (fldIt.hasNext()) {
                String fldName = fldIt.next();
                FieldItem item = fldMgr.get(fldName);
                FieldType type;
                FieldType fldtype = item.getType();
                ArrayList<String> tags = item.getTags();
                if (tags.contains("TRACK_ID")) {
                    tags.remove("TRACK_ID");
                }
                FieldDefinition fd = null;
                if (item.getCount() > 1) {
                    if (fldName.equals(joinfield)) {
                        tags.add("JOIN_ID");
                        tags.add("TRACK_ID");
                        String[] tagarr = new String[tags.size()];
                        tagarr = tags.toArray(tagarr);
                        fd = new DefaultFieldDefinition(fldName, fldtype, (String[]) tagarr);
                    } else {
                        type = FieldType.Group;
                        String[] groupedTag = { "GROUPED" };
                        fd = new DefaultFieldDefinition(fldName, type, groupedTag);
                        for (Integer i = 0; i < item.getCount(); ++i) {
                            String childName = defList.get(i);
                            FieldDefinition child = null;
                            if (tags.isEmpty()) {
                                child = new DefaultFieldDefinition(childName, fldtype);
                            } else {
                                String[] tagarr = new String[tags.size()];
                                tagarr = tags.toArray(tagarr);
                                child = new DefaultFieldDefinition(childName, fldtype, tagarr);
                            }
                            fd.addChild(child);
                        }
                    }
                } else {
                    type = fldtype;
                    if (!tags.isEmpty()) {
                        fd = new DefaultFieldDefinition(fldName, fldtype, (String[]) tags.toArray());
                    } else {
                        fd = new DefaultFieldDefinition(fldName, fldtype);
                    }

                }

                mergedFldDef.add(fd);
            }
            outDef = new DefaultGeoEventDefinition();
            outDef.setFieldDefinitions(mergedFldDef);
            outDef.setName(outdefname);
            outDef.setOwner(definition.getUri().toString());
            Collection<GeoEventDefinition> eventDefs = manager.searchGeoEventDefinitionByName(outdefname);
            Iterator<GeoEventDefinition> eventDefIt = eventDefs.iterator();
            while (eventDefIt.hasNext()) {
                GeoEventDefinition currentDef = eventDefIt.next();
                manager.deleteGeoEventDefinition(currentDef.getGuid());
            }
            manager.addGeoEventDefinition(outDef);
        } catch (ConfigurationException e) {
            LOG.error(e.getMessage());
            throw (e);
        } catch (GeoEventDefinitionManagerException e) {
            LOG.error(e.getMessage());
            throw (e);
        } catch (Exception e) {
            LOG.error(e.getMessage());
            throw (e);
        }
    }

    private GeoEvent CreateGeoEvent(HashMap<String, GeoEvent> rec) throws Exception {
        try {
            GeoEventCreator creator = messaging.createGeoEventCreator();

            GeoEvent evt = creator.create(outDef.getGuid());
            Set<String> keys = rec.keySet();
            Iterator<String> it = keys.iterator();
            while (it.hasNext()) {
                GeoEvent ge = rec.get(it.next());
                List<FieldDefinition> fldDefs = ge.getGeoEventDefinition().getFieldDefinitions();
                for (FieldDefinition fd : fldDefs) {
                    String name = fd.getName();
                    FieldItem item = fldMgr.get(name);
                    if (item.getCount() > 1) {
                        if (name.equals(joinfield)) {
                            evt.setField(joinfield, ge.getField(joinfield));
                        } else {
                            String gedname = ge.getGeoEventDefinition().getName();
                            String groupName = name + "." + gedname;
                            evt.setField(groupName, ge.getField(name));
                        }
                    } else {
                        evt.setField(name, ge.getField(name));
                    }
                }

            }
            evt.setProperty(GeoEventPropertyName.TYPE, "event");
            evt.setProperty(GeoEventPropertyName.OWNER_ID, getId());
            evt.setProperty(GeoEventPropertyName.OWNER_URI, definition.getUri());
            return evt;
        } catch (MessagingException e) {
            LOG.error(e.getMessage());
            throw (e);
        } catch (FieldException e) {
            LOG.error(e.getMessage());
            throw (e);
        } catch (Exception e) {
            LOG.error(e.getMessage());
            throw (e);
        }
    }
}