You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@felix.apache.org by pd...@apache.org on 2015/05/15 20:46:28 UTC

svn commit: r1679621 [3/3] - in /felix/sandbox/pderop/bndtools-FELIX-4866: ./ .recommenders/ .recommenders/caches/ .recommenders/index/ .recommenders/index/http___download_eclipse_org_recommenders_models_luna_/ .recommenders/repository/ .recommenders/r...

Added: felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/Unchecked.java
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/Unchecked.java?rev=1679621&view=auto
==============================================================================
--- felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/Unchecked.java (added)
+++ felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/Unchecked.java Fri May 15 18:46:25 2015
@@ -0,0 +1,103 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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.
+ */
+package org.apache.felix.framework.loadtest.scenario;
+
+import java.util.function.Consumer;
+import java.util.function.Function;
+
+/**
+ * Helper functions used to work around the java.util.function.* functions, which don't support 
+ * methods throwing a checked exception.
+ * 
+ * @author <a href="mailto:dev@felix.apache.org">Felix Project Team</a>
+ */
+public class Unchecked {
+    /**
+     * Same functional interface as java.util.function.Consumer, except that the accept method may throw an exception.
+     */
+    @FunctionalInterface
+    public static interface CheckedConsumer<T> {
+        public void accept(T t) throws Exception;
+    }
+    
+    /**
+     * Same interface as Runnable, except that the run method may throw an exception.
+     */
+    @FunctionalInterface
+    public static interface CheckedRunnable {
+        public void run() throws Exception;
+    }
+    
+    /**
+     * Same interface as Function, except that the accept method may throw an exception.
+     */
+    @FunctionalInterface
+    public static interface CheckedFunction<T,U> {
+        public U apply(T t) throws Exception;
+    }
+    
+    /**
+     * Wraps a Consumer whose accept method may throw an exception behind a regular java.util.function.Consumer
+     */
+    public static <T> Consumer<T> consumer(CheckedConsumer<T> c) {
+        return (t) -> {
+            try {
+                c.accept(t);
+            }
+            catch (Exception e) {
+                throw new RuntimeException(e);
+            }
+            catch (Throwable err) {
+                throw err;
+            }
+        };
+    }
+    
+    /**
+     * Wraps a Consumer whose accept method may throw an exception behind a regular java.util.function.Consumer
+     */
+    public static <T,U> Function<T, U> func(CheckedFunction<T, U> f) {
+        return (t) -> {
+            try {
+                return f.apply(t);
+            }
+            catch (Exception e) {
+                throw new RuntimeException(e);
+            }
+            catch (Throwable err) {
+                throw err;
+            }
+        };
+    }
+
+    /**
+     * Runs a runnable which may throw an exception without having to catch it.
+     */
+    public static void run(CheckedRunnable r) {
+        try {
+            r.run();
+        }
+        catch (Exception e) {
+            throw new RuntimeException(e);
+        }
+        catch (Throwable err) {
+            throw err;
+        }
+    }
+}

Added: felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/impl/AlbumImpl.java
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/impl/AlbumImpl.java?rev=1679621&view=auto
==============================================================================
--- felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/impl/AlbumImpl.java (added)
+++ felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/impl/AlbumImpl.java Fri May 15 18:46:25 2015
@@ -0,0 +1,68 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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.
+ */
+package org.apache.felix.framework.loadtest.scenario.impl;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+import java.util.Objects;
+
+import org.apache.felix.framework.loadtest.controller.ScenarioController;
+import org.apache.felix.framework.loadtest.scenario.Album;
+import org.apache.felix.framework.loadtest.scenario.Track;
+
+/**
+ * An album comprising several music tracks.
+ * 
+ * @author <a href="mailto:dev@felix.apache.org">Felix Project Team</a>
+ */
+public class AlbumImpl implements Album {
+    final List<Track> m_musicTracks = Collections.synchronizedList(new ArrayList<>());
+    final ScenarioController m_controller;
+    
+    public AlbumImpl(ScenarioController controller) {
+        m_controller = controller;
+    }
+    
+    public void addTrack(Track dep) {
+        Objects.nonNull(dep);
+        m_musicTracks.add(dep);
+    }
+        
+    public void start() {
+        m_controller.albumAdded(this);
+    }
+    
+    public void stop() {
+        m_controller.albumRemoved(this);
+    }
+
+    @Override
+    public List<Track> getMusicTracks() {
+        return m_musicTracks;
+    }
+
+    @Override
+    public void play() {
+        for (Track track : m_musicTracks) {
+            Objects.nonNull(track);
+            track.play();
+        }
+    }
+}

Added: felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/impl/ArtistImpl.java
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/impl/ArtistImpl.java?rev=1679621&view=auto
==============================================================================
--- felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/impl/ArtistImpl.java (added)
+++ felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/impl/ArtistImpl.java Fri May 15 18:46:25 2015
@@ -0,0 +1,67 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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.
+ */
+package org.apache.felix.framework.loadtest.scenario.impl;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+import java.util.Objects;
+
+import org.apache.felix.framework.loadtest.controller.ScenarioController;
+import org.apache.felix.framework.loadtest.scenario.Album;
+import org.apache.felix.framework.loadtest.scenario.Artist;
+
+/**
+ * One artist who depends on multiple Albums.
+ * 
+ * @author <a href="mailto:dev@felix.apache.org">Felix Project Team</a>
+ */
+public class ArtistImpl implements Artist {
+    final List<Album> m_albums = Collections.synchronizedList(new ArrayList<>());
+    final ScenarioController m_controller;
+    
+    public ArtistImpl(ScenarioController controller) {
+        m_controller = controller;
+    }
+    
+    public void addAlbum(Album dep) {
+        Objects.nonNull(dep);
+        m_albums.add(dep);
+    }
+
+    public void start() {
+        m_controller.artistAdded(this);
+    }
+    
+    public void stop() {
+        m_controller.artistRemoved(this);
+    }
+
+    @Override
+    public List<Album> getAlbums() {
+        return m_albums;
+    }
+    
+    public void play() {
+        for (Album album : m_albums) {
+            Objects.nonNull(album);
+            album.play();
+        }
+    }
+}

Added: felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/impl/TrackImpl.java
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/impl/TrackImpl.java?rev=1679621&view=auto
==============================================================================
--- felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/impl/TrackImpl.java (added)
+++ felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/scenario/impl/TrackImpl.java Fri May 15 18:46:25 2015
@@ -0,0 +1,47 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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.
+ */
+package org.apache.felix.framework.loadtest.scenario.impl;
+
+import org.apache.felix.framework.loadtest.controller.ScenarioController;
+import org.apache.felix.framework.loadtest.scenario.Track;
+
+/**
+ * One single music.
+ * 
+ * @author <a href="mailto:dev@felix.apache.org">Felix Project Team</a>
+ */
+public class TrackImpl implements Track {
+    final ScenarioController m_controller;
+
+    public TrackImpl(ScenarioController controller) {
+        m_controller = controller;
+    }
+
+    public void start() {
+        m_controller.trackAdded(this);
+    }
+    
+    public void stop() {
+        m_controller.trackRemoved(this);
+    }
+
+    @Override
+    public void play() {
+    }
+}

Added: felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/Activator.java
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/Activator.java?rev=1679621&view=auto
==============================================================================
--- felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/Activator.java (added)
+++ felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/Activator.java Fri May 15 18:46:25 2015
@@ -0,0 +1,31 @@
+package org.apache.felix.framework.loadtest.tracker;
+
+import org.apache.felix.framework.loadtest.controller.ScenarioController;
+import org.osgi.framework.BundleActivator;
+import org.osgi.framework.BundleContext;
+
+import static org.apache.felix.framework.loadtest.tracker.Component.component;
+
+/**
+ * Activator for a scenario based on Service Trackers.
+ * We'll create many Artists, each one is depending on many Albums, and each Album depends on many Tracks.
+ * 
+ * @author <a href="mailto:dev@felix.apache.org">Felix Project Team</a>
+ */
+public class Activator implements BundleActivator {
+	Component<Benchmark> m_benchmark;
+
+	@Override
+	public void start(BundleContext context) throws Exception {
+		m_benchmark = component(context, () -> new Benchmark(context))
+		    .onStart(Benchmark::start)
+		    .onStop(Benchmark::stop)
+		    .dependsOn(ScenarioController.class, null, Benchmark::bind);
+		m_benchmark.start();
+	}
+
+	@Override
+	public void stop(BundleContext context) throws Exception {
+		m_benchmark.stop();
+	}
+}

Added: felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/Benchmark.java
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/Benchmark.java?rev=1679621&view=auto
==============================================================================
--- felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/Benchmark.java (added)
+++ felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/Benchmark.java Fri May 15 18:46:25 2015
@@ -0,0 +1,82 @@
+package org.apache.felix.framework.loadtest.tracker;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.IntStream;
+import java.util.stream.Stream;
+
+import org.apache.felix.framework.loadtest.controller.ScenarioController;
+import org.apache.felix.framework.loadtest.scenario.Album;
+import org.apache.felix.framework.loadtest.scenario.Artist;
+import org.apache.felix.framework.loadtest.scenario.Helper;
+import org.apache.felix.framework.loadtest.scenario.Track;
+import org.apache.felix.framework.loadtest.scenario.impl.AlbumImpl;
+import org.apache.felix.framework.loadtest.scenario.impl.ArtistImpl;
+import org.apache.felix.framework.loadtest.scenario.impl.TrackImpl;
+import org.osgi.framework.BundleContext;
+
+import static org.apache.felix.framework.loadtest.scenario.Artist.ALBUMS;
+import static org.apache.felix.framework.loadtest.scenario.Artist.ARTISTS;
+import static org.apache.felix.framework.loadtest.scenario.Artist.TRACKS;
+import static org.apache.felix.framework.loadtest.tracker.Component.component;
+
+public class Benchmark {
+	BundleContext m_ctx;
+	ScenarioController m_controller;
+    final List<Component<?>> m_components = new ArrayList<>();
+    
+    Benchmark(BundleContext ctx) {
+    	m_ctx = ctx;
+    }
+    
+    void bind(ScenarioController controller) {
+    	m_controller = controller;
+    }
+
+    /**
+     * Initialize our Artists, Albums/Tracks, possibly using a parallel dependency manager.
+     */
+    public void start() {
+        Helper.debug(() -> "Benchmark.start");
+        
+        IntStream.range(0, ARTISTS)
+            .mapToObj(i -> createArtists()).peek(m_components::add)
+            .flatMap(artist -> createAlbums(artist)).peek(m_components::add)
+            .flatMap(album -> createTracks(album)).forEach(m_components::add);
+                            
+        m_components.stream().forEach(Component::start);
+    }
+    
+    public void stop() {
+        m_components.forEach(Component::stop);
+    }
+
+    Component<ArtistImpl> createArtists() {
+		return component(m_ctx, () -> new ArtistImpl(m_controller))
+		    .onStart(ArtistImpl::start)
+		    .onStop(ArtistImpl::stop)
+		    .provides(Artist.class, "id", Helper.generateId());
+    }
+    
+    private Stream<Component<AlbumImpl>> createAlbums(Component<ArtistImpl> artist) {
+        return IntStream.range(0, ALBUMS).mapToObj(i -> {
+            String id = Helper.generateId();
+            artist.dependsOn(Album.class, "(id=" + id + ")", ArtistImpl::addAlbum);
+            return component(m_ctx, () -> new AlbumImpl(m_controller))
+                .onStart(AlbumImpl::start)
+                .onStop(AlbumImpl::stop)
+                .provides(Album.class, "id", id);
+        });
+    }
+        
+    private Stream<Component<TrackImpl>> createTracks(Component<AlbumImpl> album) {
+        return IntStream.range(0, TRACKS).mapToObj(i -> {
+            String id = Helper.generateId();
+            album.dependsOn(Track.class, "(id=" + id + ")", AlbumImpl::addTrack);
+            return component(m_ctx, () -> new TrackImpl(m_controller))
+                .onStart(TrackImpl::start)
+                .onStop(TrackImpl::stop)
+                .provides(Track.class, "id", id);
+        });
+    }
+}

Added: felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/Component.java
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/Component.java?rev=1679621&view=auto
==============================================================================
--- felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/Component.java (added)
+++ felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/Component.java Fri May 15 18:46:25 2015
@@ -0,0 +1,147 @@
+package org.apache.felix.framework.loadtest.tracker;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Dictionary;
+import java.util.Hashtable;
+import java.util.List;
+import java.util.concurrent.Executor;
+import java.util.concurrent.atomic.AtomicBoolean;
+import java.util.concurrent.atomic.AtomicInteger;
+import java.util.function.BiConsumer;
+import java.util.function.Consumer;
+import java.util.function.Supplier;
+
+import org.apache.felix.framework.loadtest.scenario.Helper;
+import org.osgi.framework.BundleContext;
+import org.osgi.framework.ServiceRegistration;
+
+class Component<T> {
+    static volatile Executor m_tpool;
+    final Supplier<T> m_factory;
+    final BundleContext m_ctx;
+    final List<ServiceDependency<?, T>> m_dependencies = Collections.synchronizedList(new ArrayList<>());
+    Consumer<T> m_start;
+    Consumer<T> m_stop;
+    final T m_instance;
+    final AtomicInteger m_boundServices = new AtomicInteger(0);
+    AtomicBoolean m_started = new AtomicBoolean(false);
+    String m_provides;
+    Dictionary<String, ?> m_properties;
+    ServiceRegistration<?> m_registration;
+
+    static <U> Component<U> component(BundleContext ctx, Supplier<U> factory) {
+        return new Component<U>(ctx, factory);
+    }
+
+    static void setThreadPool(Executor tpool) {
+        m_tpool = tpool;
+    }
+
+    Component(BundleContext ctx, Supplier<T> factory) {
+        m_factory = factory;
+        m_ctx = ctx;
+        m_instance = factory.get();
+    }
+
+    T getInstance() {
+        return m_instance;
+    }
+
+    Component<T> onStart(Consumer<T> start) {
+        m_start = start;
+        return this;
+    }
+
+    Component<T> onStop(Consumer<T> stop) {
+        m_stop = stop;
+        return this;
+    }
+
+    <U> Component<T> provides(Class<U> service, Object... properties) {
+        m_provides = service.getName();
+        if (properties.length > 0) {
+            Hashtable<String, Object> props = new Hashtable<>();
+            if ((properties.length & 1) != 0) {
+                throw new IllegalArgumentException(
+                    "Invalid number of specified properties (number of arguments must be even).");
+            }
+            for (int i = 0; i < properties.length - 1; i += 2) {
+                String key = properties[i].toString().trim();
+                Object value = properties[i + 1];
+                props.put(key, value);
+            }
+            m_properties = props;
+        }
+        return this;
+    }
+
+    <U> Component<T> dependsOn(Class<U> service, String filter, BiConsumer<T, U> added) {
+        m_dependencies.add(new ServiceDependency<U, T>(m_ctx, service, filter, this, added));
+        return this;
+    }
+
+    void start() {
+        Runnable task = new Runnable() {
+            @Override
+            public void run() {
+                if (m_dependencies.size() == 0) {
+                    doStart();
+                } else {
+                    m_dependencies.stream().forEach(dependency -> dependency.open());
+                }
+            }
+        };
+        
+        if (m_tpool != null) {
+            m_tpool.execute(task);
+        } else {
+            task.run();
+        }
+    }
+
+    void stop() {
+        if (m_dependencies.size() == 0) {
+            doStop();
+        } else {
+            m_dependencies.stream().forEach(dependency -> dependency.close());
+        }
+    }
+
+    public void addedService() {
+        if (m_boundServices.incrementAndGet() == m_dependencies.size()) {
+            doStart();
+        }
+    }
+
+    public void removedService() {
+    	if (m_boundServices.decrementAndGet() == 0) {
+    		doStop();
+    	}
+    }
+
+    private void doStart() {
+	    if (m_started.compareAndSet(false, true)) {
+            if (m_start != null) {
+                m_start.accept(m_instance);
+            }
+
+            if (m_provides != null) {
+            	Helper.debug(() -> "registering component " + m_instance + "; " + m_provides);
+                m_registration = m_ctx.registerService(m_provides, m_instance, m_properties);
+            }
+	    }
+	}
+
+    private void doStop() {
+        if (m_started.compareAndSet(true, false)) {
+            if (m_stop != null) {
+                m_stop.accept(m_instance);
+            }
+
+            if (m_registration != null) {
+            	m_registration.unregister();
+            }
+        }
+    }
+}
\ No newline at end of file

Added: felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/ParallelActivator.java
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/ParallelActivator.java?rev=1679621&view=auto
==============================================================================
--- felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/ParallelActivator.java (added)
+++ felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/ParallelActivator.java Fri May 15 18:46:25 2015
@@ -0,0 +1,12 @@
+package org.apache.felix.framework.loadtest.tracker;
+
+import org.apache.felix.framework.loadtest.scenario.Helper;
+import org.osgi.framework.BundleContext;
+
+public class ParallelActivator extends Activator {
+    @Override
+    public void start(BundleContext context) throws Exception {
+        Component.setThreadPool(Helper.getThreadPool());
+        super.start(context);
+    }
+}

Added: felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/ServiceDependency.java
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/ServiceDependency.java?rev=1679621&view=auto
==============================================================================
--- felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/ServiceDependency.java (added)
+++ felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/src/org/apache/felix/framework/loadtest/tracker/ServiceDependency.java Fri May 15 18:46:25 2015
@@ -0,0 +1,66 @@
+package org.apache.felix.framework.loadtest.tracker;
+
+import java.util.function.BiConsumer;
+
+import org.osgi.framework.BundleContext;
+import org.osgi.framework.Constants;
+import org.osgi.framework.InvalidSyntaxException;
+import org.osgi.framework.ServiceReference;
+import org.osgi.util.tracker.ServiceTracker;
+import org.osgi.util.tracker.ServiceTrackerCustomizer;
+
+class ServiceDependency<T, U> implements ServiceTrackerCustomizer<T, T> {
+	final Class<T> m_service;
+	final String m_filter;
+	final BundleContext m_ctx;
+	final Component<U> m_component;
+	final BiConsumer<U, T> m_added;
+
+	ServiceTracker<T, T> m_tracker;
+	
+	ServiceDependency(BundleContext ctx, Class<T> service, String filter, Component<U> component, BiConsumer<U, T> added) {
+		m_ctx = ctx;
+		m_service = service;
+		m_filter = filter;
+		m_component = component;
+		m_added = added;
+	}
+		
+	void open() {
+		if (m_filter != null) {
+			String filter = "(&(" + Constants.OBJECTCLASS + "=" + m_service.getName() + ")" + m_filter + ")";
+			try {
+				m_tracker = new ServiceTracker<>(m_ctx, m_ctx.createFilter(filter), this);
+			} catch (InvalidSyntaxException e) {
+				e.printStackTrace();
+			}
+		} else {
+			m_tracker = new ServiceTracker<>(m_ctx, m_service.getName(), this);
+		}
+		m_tracker.open();
+	}
+	
+	void close() {
+		m_tracker.close();
+	}
+
+	@Override
+	public T addingService(ServiceReference<T> reference) {
+		T service = (T) m_ctx.getService(reference);
+		m_added.accept(m_component.getInstance(), service);
+		m_component.addedService();
+		return service;
+	}
+
+	@Override
+	public void modifiedService(ServiceReference<T> reference, T service) {
+		// TODO Auto-generated method stub
+		
+	}
+
+	@Override
+	public void removedService(ServiceReference<T> reference, T service) {
+	    m_ctx.ungetService(reference);
+		m_component.removedService();
+	}
+}

Added: felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/test/.gitignore
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/test/.gitignore?rev=1679621&view=auto
==============================================================================
    (empty)

Added: felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/tracker.bnd
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/tracker.bnd?rev=1679621&view=auto
==============================================================================
--- felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/tracker.bnd (added)
+++ felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/tracker.bnd Fri May 15 18:46:25 2015
@@ -0,0 +1,3 @@
+Private-Package:  \
+	org.apache.felix.framework.loadtest.tracker
+Bundle-Activator: org.apache.felix.framework.loadtest.tracker.Activator
\ No newline at end of file

Added: felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/tracker.parallel.bnd
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/tracker.parallel.bnd?rev=1679621&view=auto
==============================================================================
--- felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/tracker.parallel.bnd (added)
+++ felix/sandbox/pderop/bndtools-FELIX-4866/org.apache.felix.framework.loadtest/tracker.parallel.bnd Fri May 15 18:46:25 2015
@@ -0,0 +1,3 @@
+Private-Package:  \
+	org.apache.felix.framework.loadtest.tracker
+Bundle-Activator: org.apache.felix.framework.loadtest.tracker.ParallelActivator
\ No newline at end of file

Added: felix/sandbox/pderop/bndtools-FELIX-4866/settings.gradle
URL: http://svn.apache.org/viewvc/felix/sandbox/pderop/bndtools-FELIX-4866/settings.gradle?rev=1679621&view=auto
==============================================================================
--- felix/sandbox/pderop/bndtools-FELIX-4866/settings.gradle (added)
+++ felix/sandbox/pderop/bndtools-FELIX-4866/settings.gradle Fri May 15 18:46:25 2015
@@ -0,0 +1,127 @@
+/*
+ * Master Gradle initialization script
+ *
+ * Depends on bnd_* values from gradle.properties.
+ */
+
+import aQute.bnd.build.Workspace
+
+/* Add bnd as a script dependency */
+buildscript {
+  dependencies {
+    def bndURI = rootDir.toURI().resolve(bnd_jar)
+    if (bndURI.scheme != 'file') {
+      /* If not a local file, copy to a local file in cnf/cache */
+      def cnfCache = mkdir("${rootDir}/${bnd_cnf}/cache")
+      def bndJarFile = new File(cnfCache, 'biz.aQute.bnd.gradle.jar')
+      if (!bndJarFile.exists()) {
+        println "Downloading ${bndURI} to ${bndJarFile} ..."
+        bndURI.toURL().withInputStream { is ->
+          bndJarFile.withOutputStream { os ->
+            def bos = new BufferedOutputStream( os )
+            bos << is
+          }
+        }
+      }
+      bndURI = bndJarFile.toURI()
+    }
+    classpath files(bndURI)
+
+    /* After the rootProject is created, pass URI to projects */
+    gradle.rootProject { rootProject ->
+      rootProject.ext.bndURI = bndURI
+    }
+  }
+}
+
+/* Initialize the bnd workspace */
+def workspace = Workspace.getWorkspace(rootDir, bnd_cnf)
+if (workspace == null) {
+  throw new GradleException("Unable to load workspace ${rootDir}/${bnd_cnf}")
+}
+
+/* Add cnf project to the graph */
+include bnd_cnf
+
+/* Start with the declared build project name */
+def defaultProjectName = bnd_build
+
+/* If in a subproject, use the subproject name */
+for (def currentDir = startParameter.currentDir; currentDir != rootDir; currentDir = currentDir.parentFile) {
+  defaultProjectName = currentDir.name
+}
+
+/* Build a set of project names we need to include from the specified tasks */
+def projectNames = startParameter.taskNames.collect { taskName ->
+  def elements = taskName.split(':')
+  switch (elements.length) {
+    case 1:
+      return defaultProjectName
+    case 2:
+      return elements[0].empty ? bnd_build : elements[0]
+    default:
+      return elements[0].empty ? elements[1] : elements[0]
+  }
+}.toSet()
+
+/* Include the default project name if in a subproject or no tasks specified */
+if ((startParameter.currentDir != rootDir) || projectNames.empty) {
+  projectNames += defaultProjectName
+}
+
+/* If bnd_build used but declared empty, add all non-private folders of rootDir */
+if (projectNames.remove('')) {
+  rootDir.eachDir {
+    def projectName = it.name
+    if (!projectName.startsWith('.')) {
+      projectNames += projectName
+    }
+  }
+}
+
+/* Add each project and its dependencies to the graph */
+projectNames.each { projectName ->
+  include projectName
+  def project = getBndProject(workspace, projectName)
+  project?.dependson.each {
+    include it.name
+  }
+}
+
+/* Get the bnd project for the specified project name */
+def getBndProject(Workspace workspace, String projectName) {
+  def project = workspace.getProject(projectName)
+  if (project == null) {
+    return null
+  }
+  project.prepare()
+  if (project.isValid()) {
+    return project
+  }
+
+  project.getInfo(workspace, "${rootDir} :")
+  def errorCount = 0
+  project.warnings.each {
+    println "Warning: ${it}"
+  }
+  project.errors.each {
+    println "Error  : ${it}"
+    errorCount++
+  }
+  if (!project.isOk()) {
+    def str = 'even though no errors were reported'
+    if (errorCount == 1) {
+      str = 'one error was reported'
+    } else if (errorCount > 1) {
+      str = "${errorCount} errors were reported"
+    }
+    throw new GradleException("Project ${rootDir}/${projectName} is invalid, ${str}")
+  }
+  throw new GradleException("Project ${rootDir}/${projectName} is not a valid bnd project")
+}
+
+/* After the rootProject is created, set up some properties. */
+gradle.rootProject { rootProject ->
+  rootProject.ext.bndWorkspace = workspace
+  rootProject.ext.cnf = rootProject.project(bnd_cnf)
+}