Skip to content

Commit

Permalink
Demonstrating CDI in kernel
Browse files Browse the repository at this point in the history
  • Loading branch information
ajs6f committed Feb 15, 2013
1 parent ff2ea5d commit a3ab4a9
Show file tree
Hide file tree
Showing 28 changed files with 512 additions and 594 deletions.
36 changes: 26 additions & 10 deletions fcrepo-kernel/pom.xml
Expand Up @@ -15,6 +15,10 @@

<description>The Fedora repository kernel</description>

<properties>
<ops4j.version>3.0.0</ops4j.version>
</properties>

<dependencies>
<dependency>
<groupId>org.modeshape</groupId>
Expand All @@ -40,39 +44,51 @@
<groupId>org.jboss.jbossts</groupId>
<artifactId>jbossjta</artifactId>
</dependency>

<!-- Logging: we'll use LogBack (which implements the SLF4J API); ModeShape
knows what to do. -->
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<groupId>javax.enterprise</groupId>
<artifactId>cdi-api</artifactId>
</dependency>
<dependency>
<groupId>javax.inject</groupId>
<artifactId>javax.inject</artifactId>
</dependency>
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>guava</artifactId>
</dependency>
<dependency>
<!-- spring-test (v. 3.2.0-RELEASE) currently depends on commons-logging -->
<groupId>org.slf4j</groupId>
<artifactId>jcl-over-slf4j</artifactId>
</dependency>
<!-- Logging: we'll use LogBack (which implements the SLF4J API); ModeShape
knows what to do. -->
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
</dependency>
<!-- test gear -->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<artifactId>spring-beans</artifactId>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-beans</artifactId>
<groupId>org.ops4j.pax.exam</groupId>
<artifactId>pax-exam-container-openwebbeans</artifactId>
<version>${ops4j.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>guava</artifactId>
<groupId>org.ops4j.pax.exam</groupId>
<artifactId>pax-exam-junit4</artifactId>
<version>${ops4j.version}</version>
<scope>test</scope>
</dependency>

</dependencies>

<build>
Expand Down
@@ -0,0 +1,8 @@

package org.fcrepo;

public enum FedoraResourceType {

Object, Datastream;

}
75 changes: 75 additions & 0 deletions fcrepo-kernel/src/main/java/org/fcrepo/eventing/DefaultFilter.java
@@ -0,0 +1,75 @@

package org.fcrepo.eventing;

import static com.google.common.collect.Iterables.any;
import static com.google.common.collect.Sets.newHashSet;

import javax.annotation.PostConstruct;
import javax.annotation.PreDestroy;
import javax.enterprise.inject.Default;
import javax.inject.Inject;
import javax.jcr.LoginException;
import javax.jcr.PathNotFoundException;
import javax.jcr.RepositoryException;
import javax.jcr.Session;
import javax.jcr.nodetype.NodeType;
import javax.jcr.observation.Event;

import org.modeshape.common.SystemFailureException;
import org.modeshape.jcr.api.Repository;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.google.common.base.Predicate;

@Default
public class DefaultFilter implements EventFilter {

final private Logger logger = LoggerFactory.getLogger(DefaultFilter.class);

@Inject
private Repository repository;

// it's safe to keep the session around, because this code does not mutate
// the state of the repository
private Session session;

private Predicate<NodeType> isFedoraNodeType = new Predicate<NodeType>() {

@Override
public boolean apply(NodeType type) {
return type.getName().startsWith("fedora:");
}
};

@Override
public boolean apply(Event event) {

try {
// logger.debug("Filtering on event: " + event.toString());
return any(newHashSet(session.getNode(event.getPath())
.getMixinNodeTypes()), isFedoraNodeType);

} catch (PathNotFoundException e) {
return false; // not a node in the fedora workspace
} catch (LoginException e) {
throw new SystemFailureException(e);
} catch (RepositoryException e) {
throw new SystemFailureException(e);
}
}

@PostConstruct
public void acquireSession() {
try {
session = repository.login();
} catch (RepositoryException e) {
throw new IllegalStateException(e);
}
}

@PreDestroy
public void releaseSession() {
session.logout();
}
}
@@ -1,4 +1,4 @@
package org.fcrepo.observer;
package org.fcrepo.eventing;

import javax.jcr.observation.Event;

Expand Down
12 changes: 12 additions & 0 deletions fcrepo-kernel/src/main/java/org/fcrepo/eventing/FedoraEvent.java
@@ -0,0 +1,12 @@

package org.fcrepo.eventing;

import javax.jcr.observation.Event;

import org.fcrepo.FedoraResourceType;

public interface FedoraEvent extends Event {

public FedoraResourceType getResourceType();

}
@@ -0,0 +1,25 @@

package org.fcrepo.eventing;

import javax.inject.Singleton;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.google.common.eventbus.EventBus;

@Singleton
public class FedoraEventBus extends EventBus {

final private Logger logger = LoggerFactory.getLogger(FedoraEventBus.class);

public void post(FedoraEvent event) {
logger.debug("Received posting: " + event.toString());
super.post(event);
}

public FedoraEventBus() {
super();
logger.debug("Created Fedora event bus.");
}
}
@@ -1,7 +1,9 @@
package org.fcrepo.observer;
package org.fcrepo.eventing;

import javax.enterprise.inject.Alternative;
import javax.jcr.observation.Event;

@Alternative
public class NOOPFilter implements EventFilter {
@Override
public boolean apply(Event event) {
Expand Down
@@ -0,0 +1,94 @@

package org.fcrepo.eventing;

import static com.google.common.collect.Collections2.filter;
import static org.fcrepo.FedoraResourceType.Datastream;
import static org.fcrepo.FedoraResourceType.Object;
import static org.fcrepo.utils.FedoraTypesUtils.isFedoraDatastream;
import static org.fcrepo.utils.FedoraTypesUtils.isFedoraObject;

import javax.annotation.PostConstruct;
import javax.annotation.PreDestroy;
import javax.enterprise.inject.Default;
import javax.inject.Inject;
import javax.jcr.Node;
import javax.jcr.RepositoryException;
import javax.jcr.Session;
import javax.jcr.observation.Event;
import javax.jcr.observation.EventIterator;
import javax.jcr.observation.EventListener;

import org.fcrepo.FedoraResourceType;
import org.fcrepo.eventing.impl.FedoraEventImpl;
import org.modeshape.jcr.api.Repository;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.google.common.collect.ImmutableList.Builder;

@Default
public class SimpleObserver implements EventListener {

final private Integer eventTypes = Event.NODE_ADDED + Event.NODE_REMOVED +
Event.NODE_MOVED + Event.PROPERTY_ADDED + Event.PROPERTY_CHANGED +
Event.PROPERTY_REMOVED;

@Inject
private Repository repository;

@Inject
public FedoraEventBus eventBus;

@Inject
private EventFilter eventFilter;

private Session session;

final private Logger logger = LoggerFactory.getLogger(SimpleObserver.class);

@PostConstruct
public void buildListener() {
logger.debug("Initializing " + this.getClass().getCanonicalName());
try {
session = repository.login();
session.getWorkspace().getObservationManager().addEventListener(
this, eventTypes, "/", true, null, null, false);
session.save();
} catch (RepositoryException e) {
throw new IllegalStateException(e);
}
}

// it's okay to suppress type-safety warning here,
// because we know that EventIterator only produces
// Events, like an Iterator<Event>
@SuppressWarnings("unchecked")
@Override
public void onEvent(EventIterator events) {
logger.debug("Received " + events.getSize() + " JCR events.");
for (Event e : filter(new Builder<Event>().addAll(events).build(),
eventFilter)) {
logger.debug("Putting event: " + e.toString() + " on the bus.");
FedoraResourceType type = null;
try {
Node n = session.getNode(e.getPath());
if (isFedoraObject.apply(n)) {
type = Object;
}
if (isFedoraDatastream.apply(n)) {
type = Datastream;
}
} catch (RepositoryException e1) {
throw new IllegalStateException(e1);
}
FedoraEvent fe = new FedoraEventImpl(e, type);
eventBus.post(fe);
}
}

@PreDestroy
public void logoutSession() {
session.logout();
}

}
@@ -0,0 +1,64 @@

package org.fcrepo.eventing.impl;

import java.util.Map;

import javax.jcr.RepositoryException;
import javax.jcr.observation.Event;

import org.fcrepo.FedoraResourceType;
import org.fcrepo.eventing.FedoraEvent;

public class FedoraEventImpl implements FedoraEvent {

Event event;

FedoraResourceType type;

public FedoraEventImpl(Event event, FedoraResourceType type) {
this.event = event;
this.type = type;
}

@Override
public int getType() {
return event.getType();
}

@Override
public String getPath() throws RepositoryException {
return event.getPath();
}

@Override
public String getUserID() {
return event.getUserID();
}

@Override
public String getIdentifier() throws RepositoryException {
return event.getIdentifier();
}

@Override
public Map getInfo() throws RepositoryException {
return event.getInfo();
}

@Override
public String getUserData() throws RepositoryException {
return event.getUserData();
}

@Override
public long getDate() throws RepositoryException {
return event.getDate();
}

@Override
public FedoraResourceType getResourceType() {

return null;
}

}
@@ -0,0 +1,21 @@

package org.fcrepo.jcr;

import java.net.MalformedURLException;
import java.net.URL;

import javax.enterprise.context.ApplicationScoped;
import javax.enterprise.inject.Default;
import javax.enterprise.inject.Produces;

@ApplicationScoped
@Default
public class DefaultConfiguration {

@Produces
@ModeShapeRepositoryConfiguration
public URL getConfiguration() throws MalformedURLException {
return this.getClass().getResource("/repository.json");
}

}

0 comments on commit a3ab4a9

Please sign in to comment.