Package com.hp.hpl.jena.gvs.impl.memory

Source Code of com.hp.hpl.jena.gvs.impl.memory.NativeMemoryMetaStore

/*
  (c) Copyright 2005, 2006, Hewlett-Packard Development Company, LP
    [See end of file]
   $Id: NativeMemoryMetaStore.java,v 1.5 2007/06/27 12:50:14 rebach Exp $
*/
package com.hp.hpl.jena.gvs.impl.memory;

import java.util.Comparator;
import java.util.Date;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;
import java.util.SortedSet;
import java.util.TreeSet;

import org.wymiwyg.rdf.graphs.NamedNode;
import org.wymiwyg.rdf.graphs.impl.NamedNodeImpl;

import com.hp.hpl.jena.datatypes.xsd.XSDDateTime;
import com.hp.hpl.jena.gvs.Source;
import com.hp.hpl.jena.gvs.StoreException;
import com.hp.hpl.jena.gvs.impl.METAMODEL;
import com.hp.hpl.jena.gvs.impl.SourceImpl;
import com.hp.hpl.jena.gvs.storage.MetaStore;
import com.hp.hpl.jena.rdf.model.Literal;
import com.hp.hpl.jena.rdf.model.Model;
import com.hp.hpl.jena.rdf.model.ResIterator;
import com.hp.hpl.jena.rdf.model.Resource;
import com.hp.hpl.jena.rdf.model.StmtIterator;
import com.hp.hpl.jena.vocabulary.RDF;

/**
* An implementation of <code>MetaStore</code> using HashMaps and TreeSet to
* store the data.
*
* @author reto
*/
public class NativeMemoryMetaStore implements MetaStore {

  /**
   * Allows to associate revocations and assertions (events) to a moment. For
   * equals/hashcode and sorting only the date is relevant, the using code has
   * to make sure all events happening at the same moment are stored in the
   * same object. The natural order is the inverse of Date (i.e. more recent
   * dates are 'smaller')
   *
   * @author reto
   *
   */
  private class RelevantMoment implements Comparable<RelevantMoment> {

    Set<SourceComponent> assertions = new HashSet<SourceComponent>();
    Date moment;
    Set<SourceComponent> revocations = new HashSet<SourceComponent>();

    /**
     * the source that in this moment revoke all except what the assert in
     * this moment
     */
    Set<Source> revokeAllSources = new HashSet<Source>();

    RelevantMoment(Date moment) {
      this.moment = moment;
    }

    /*
     * (non-Javadoc)
     *
     * @see java.lang.Comparable#compareTo(java.lang.Object)
     */
    public int compareTo(RelevantMoment o) {
      return -moment.compareTo(o.moment);
    }

    @Override
    public boolean equals(Object obj) {
      RelevantMoment other = (RelevantMoment) obj;
      return other.moment.equals(moment);
    }

    @Override
    public int hashCode() {
      return moment.hashCode();
    }
  }

  /**
   * associated a source and a component
   */
  private class SourceComponent {
    NamedNode moleculeRef;
    Source source;

    SourceComponent(Source source, NamedNode moleculeRef) {
      this.source = source;
      this.moleculeRef = moleculeRef;
    }

    @Override
    public boolean equals(Object obj) {
      SourceComponent other = (SourceComponent) obj;
      return other.moleculeRef.equals(moleculeRef)
          && source.equals(source);
    }

    @Override
    public int hashCode() {
      return moleculeRef.hashCode() ^ source.hashCode();
    }
  }

  private Map<NamedNode, Resource> componentTypeMap = new HashMap<NamedNode, Resource>();
  private SortedSet<Date> eventDates = new TreeSet<Date>();
  private Map<Date, RelevantMoment> relevantMomentsMap = new HashMap<Date, RelevantMoment>();
  private Map<SourceComponent, SortedSet<RelevantMoment>> whatWhenMap = new HashMap<SourceComponent, SortedSet<RelevantMoment>>();
  private Map<Source, SortedSet<RelevantMoment>> whoWhat = new HashMap<Source, SortedSet<RelevantMoment>>();

  public boolean assertComponent(Source source, NamedNode moleculeRef,
      Date moment, Resource type) {
    SourceComponent sourceComponent = new SourceComponent(source,
        moleculeRef);
    componentTypeMap.put(moleculeRef, type);
    SortedSet<RelevantMoment> existingMoments = whatWhenMap
        .get(sourceComponent);
    RelevantMoment relevantMoment;
    if (existingMoments != null) {
      RelevantMoment lastMoment = existingMoments.first();
      if (lastMoment.assertions.contains(sourceComponent)) {
        return false;
      }
      // otherwise the component was revoked in the last relevant moment
      // for this sourceComponent
      if (lastMoment.moment.equals(moment)) {
        relevantMoment = lastMoment;
      } else {
        relevantMoment = getRelevantMoment(moment);
        existingMoments.add(relevantMoment);
        putToValueSet(whoWhat, source, relevantMoment);
      }
    } else {
      existingMoments = new TreeSet<RelevantMoment>();
      whatWhenMap.put(sourceComponent, existingMoments);
      relevantMoment = getRelevantMoment(moment);
      existingMoments.add(relevantMoment);
      putToValueSet(whoWhat, source, relevantMoment);
    }
    relevantMoment.assertions.add(sourceComponent);
    return true;
  }

  public Set<NamedNode> getAsserted(Set<Source> sources, Date moment,
      Resource type) {
    // Go back the relevantMoment for every source till there is with a
    // SourceRevokeAll for this source, for this, there should be
    // 1) a revoleAll(source, moment) method
    // 2) (possibly) revokeComponent(...) should occasionally (like every
    // 100 relevantMoments) make a revokeAll combined with the re-assertions
    // of the remaining molecules
    Set<NamedNode> result = new HashSet<NamedNode>();
    for (Source source : sources) {
      Set<NamedNode> revocations = new HashSet<NamedNode>();
      SortedSet<RelevantMoment> relevantMoments = whoWhat.get(source);
      RelevantMoment fromElement = new RelevantMoment(moment);
      if (relevantMoments == null) {
        continue;
      }
      SortedSet<RelevantMoment> relevantMomentsInTimeRange = relevantMoments
          .tailSet(fromElement);
      for (RelevantMoment relevantMoment : relevantMomentsInTimeRange) {
        for (SourceComponent assertion : relevantMoment.assertions) {
          if (!assertion.source.equals(source)) {
            continue;
          }
          // check if this source has revoked that compoent after the
          // current relevantMoment
          if (revocations.contains(assertion.moleculeRef)) {
            continue;
          }
          // TODO does the type really belongs in the metastore?
          if (!componentTypeMap.get(assertion.moleculeRef).equals(
              type)) {
            continue;
          }
          result.add(assertion.moleculeRef);
        }
        for (SourceComponent revocation : relevantMoment.revocations) {
          if (!revocation.source.equals(source)) {
            continue;
          }
          // not checking type
          revocations.add(revocation.moleculeRef);
        }
        if (relevantMoment.revokeAllSources.contains(source)) {
          break;
        }
      }
    }
    return result;
  }

  public Iterator<Date> getFollowingChanges(Set<Source> sources, Date moment) {
    SortedSet<RelevantMoment> resultSortedSet = new TreeSet<RelevantMoment>(
        new Comparator<RelevantMoment>() {

          public int compare(RelevantMoment o1, RelevantMoment o2) {
            return o2.compareTo(o1);
          }

        });
    for (Source source : sources) {
      SortedSet<RelevantMoment> moments = whoWhat.get(source);
      if (moments == null) {
        continue;
      }
      RelevantMoment toElement = new RelevantMoment(moment);
      resultSortedSet.addAll(moments.headSet(toElement));
    }
    final Iterator<RelevantMoment> baseIter = resultSortedSet.iterator();
    return new Iterator<Date>() {

      public boolean hasNext() {
        return baseIter.hasNext();
      }

      public Date next() {
        return baseIter.next().moment;
      }

      public void remove() {
        throw new UnsupportedOperationException();
       
      }
     
    };
   
  }

  public Iterator<Date> getPreviousChanges(Set<Source> sources, Date moment) {
    SortedSet<RelevantMoment> resultSortedSet = new TreeSet<RelevantMoment>();
    for (Source source : sources) {
      SortedSet<RelevantMoment> moments = whoWhat.get(source);
      RelevantMoment toElement = new RelevantMoment(moment);
      resultSortedSet.addAll(moments.tailSet(toElement));
    }
    final Iterator<RelevantMoment> baseIter = resultSortedSet.iterator();
    return new Iterator<Date>() {

      public boolean hasNext() {
        return baseIter.hasNext();
      }

      public Date next() {
        return baseIter.next().moment;
      }

      public void remove() {
        throw new UnsupportedOperationException();
       
      }
     
    };

  }

  /*
   * (non-Javadoc)
   *
   * @see com.hp.hpl.jena.gvs.storage.MetaStore#getSources()
   */
  public Set<Source> getSources() {
    return whoWhat.keySet();
  }

  /*
   * (non-Javadoc)
   *
   * @see com.hp.hpl.jena.gvs.storage.MetaStore#revokeComponent(com.hp.hpl.jena.gvs.Source,
   *      org.wymiwyg.rdf.graphs.NamedNode, java.util.Date)
   */
  public void revokeComponent(Source source, NamedNode moleculeRef,
      Date moment) {
    SourceComponent sourceComponent = new SourceComponent(source,
        moleculeRef);
    SortedSet<RelevantMoment> existingRelevantMoments = whoWhat.get(source);
    for (RelevantMoment relevantMoment : existingRelevantMoments) {
      if (relevantMoment.assertions.contains(sourceComponent)) {
        break;
      }
      if (relevantMoment.revocations.contains(sourceComponent)) {
        throw new StoreException(
            "Assertion "+moleculeRef+" of source "+source+" not found (already revoked at "+relevantMoment.moment+" which is before "+moment+")");
      }
      if (relevantMoment.revokeAllSources.contains(source)) {
        throw new StoreException(
            "Assertion "+moleculeRef+" of source "+source+" not found (not between "+relevantMoment.moment+" and "+moment+")");
      }
    }
    RelevantMoment relevantMoment = getRelevantMoment(moment);

    relevantMoment.revocations.add(sourceComponent);
    putToValueSet(whatWhenMap, sourceComponent, relevantMoment);
    putToValueSet(whoWhat, source, relevantMoment);

  }

  /**
   * @param moment
   * @return
   */
  private RelevantMoment getRelevantMoment(Date moment) {
    RelevantMoment relevantMoment = relevantMomentsMap.get(moment);
    if (relevantMoment == null) {
      relevantMoment = new RelevantMoment(moment);
      relevantMomentsMap.put(moment, relevantMoment);
      eventDates.add(moment);
    }
    return relevantMoment;
  }

  private <K, V> void putToValueSet(Map<K, SortedSet<V>> map, K key, V value) {
    SortedSet<V> valueSet = map.get(key);
    if (valueSet == null) {
      valueSet = new TreeSet<V>();
      map.put(key, valueSet);
    }
    valueSet.add(value);

  }

  /* (non-Javadoc)
   * @see com.hp.hpl.jena.gvs.storage.MetaStore#getAssertions(com.hp.hpl.jena.gvs.Source, java.util.Date, com.hp.hpl.jena.rdf.model.Resource)
   */
  public Set<NamedNode> getAssertions(Source source, Date moment,
      Resource type) {
    Set<NamedNode> result = new HashSet<NamedNode>();
    for (SourceComponent assertion : relevantMomentsMap.get(moment).assertions) {
      if (assertion.source.equals(source)) {
        result.add(assertion.moleculeRef);
      }
    }
    return result;
  }

  /* (non-Javadoc)
   * @see com.hp.hpl.jena.gvs.storage.MetaStore#getRevocations(com.hp.hpl.jena.gvs.Source, java.util.Date, com.hp.hpl.jena.rdf.model.Resource)
   */
  public Set<NamedNode> getRevocations(Source source, Date moment,
      Resource type) {
    Set<NamedNode> result = new HashSet<NamedNode>();
    for (SourceComponent revocation : relevantMomentsMap.get(moment).revocations) {
      if (revocation.source.equals(source)) {
        result.add(revocation.moleculeRef);
      }
    }
    return result;
  }

  /**
   * @param metaModel
   */
  public void loadFromModel(Model metaModel) {
//    ResIterator  resIterator = metaModel.listSubjectsWithProperty(RDF.type,
//        METAMODEL.Assertion);
    ResIterator  resIterator = metaModel.listSubjectsWithProperty(METAMODEL.asserter);
    while (resIterator.hasNext()) {
      Resource assertion = resIterator.nextResource();
     
      Resource assertedComponent = assertion.getProperty(
          METAMODEL.assertedComponent).getResource();
      Resource type = null;
      StmtIterator typeIter = assertedComponent.listProperties(RDF.type);
      while (typeIter.hasNext()) {
        Resource currentType = typeIter.nextStatement().getResource();
        if (currentType.getNameSpace().equals(METAMODEL.getURI())) {
          type = currentType;
          break;
        }
      }
      Resource assertionSource = assertion.getProperty(
          METAMODEL.asserter).getResource();
      Source source = new SourceImpl(assertionSource.getURI());
      NamedNode component = new NamedNodeImpl(assertedComponent.getURI());
      componentTypeMap.put(component, type);
      SourceComponent sourceComponent = new SourceComponent(source, component);
      {
        //adding assertion
        Literal assertionTimeLit = assertion.getProperty(
            METAMODEL.assertionTime).getLiteral();
        Date assertionTime = ((XSDDateTime) assertionTimeLit.getValue())
        .asCalendar().getTime();
        RelevantMoment relevantMoment = getRelevantMoment(assertionTime);
        relevantMoment.assertions.add(sourceComponent);
        putToValueSet(whatWhenMap, sourceComponent, relevantMoment);
        putToValueSet(whoWhat, source, relevantMoment);
      }
      if (assertion.hasProperty(METAMODEL.revocationTime)) {
        Literal revocationTimeLit = assertion.getProperty(
            METAMODEL.revocationTime).getLiteral();
        Date revocationTime = ((XSDDateTime) revocationTimeLit.getValue())
        .asCalendar().getTime();
        RelevantMoment relevantMoment = getRelevantMoment(revocationTime);
        relevantMoment.revocations.add(sourceComponent);
        putToValueSet(whatWhenMap, sourceComponent, relevantMoment);
        putToValueSet(whoWhat, source, relevantMoment);
      }
    }
   
  }

}

/*
* (c) Copyright 2005, 2006 Hewlett-Packard Development Company, LP All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
* EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
 
TOP

Related Classes of com.hp.hpl.jena.gvs.impl.memory.NativeMemoryMetaStore

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.