blob: d775f071408998f3b656eda19279006b2813972e [file] [log] [blame]
/**********************************************************************
* This file is part of "Object Teams Development Tooling"-Software
*
* Copyright 2013 GK Software AG
*
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Please visit http://www.objectteams.org for updates and contact.
*
* Contributors:
* Stephan Herrmann - Initial API and implementation
**********************************************************************/
package org.eclipse.objectteams.internal.osgi.weaving;
import static org.eclipse.objectteams.otequinox.Activator.log;
import java.util.ArrayList;
import java.util.List;
import org.eclipse.core.runtime.IStatus;
import org.osgi.framework.Bundle;
/**
* Each instance of this class represents the fact that a given base bundle has aspect bindings,
* which require to load / instantiate / activate one or more teams at a suitable point in time.
*/
public class BaseBundleLoadTrigger {
private AspectBindingRegistry aspectBindingRegistry;
@SuppressWarnings("deprecation")
private org.osgi.service.packageadmin.PackageAdmin admin;
private String baseBundleName;
private boolean teamsScanned = false;
public BaseBundleLoadTrigger(String bundleSymbolicName, AspectBindingRegistry aspectBindingRegistry,
@SuppressWarnings("deprecation") org.osgi.service.packageadmin.PackageAdmin admin)
{
this.baseBundleName = bundleSymbolicName;
this.aspectBindingRegistry = aspectBindingRegistry;
this.admin = admin;
}
/** Signal that the given class is being loaded and trigger any necessary loading/instantiation/activation. */
public void fire(String className) {
List<AspectBindingRegistry.WaitingTeamRecord> deferredTeamClasses = new ArrayList<>();
List<AspectBinding> aspectBindings = aspectBindingRegistry.getAdaptingAspectBindings(baseBundleName);
if (aspectBindings != null) {
for (AspectBinding aspectBinding : aspectBindings) {
if (aspectBinding.activated)
continue;
@SuppressWarnings("deprecation")
Bundle[] aspectBundles = admin.getBundles(aspectBinding.aspectPlugin, null);
if (aspectBundles == null || aspectBundles.length == 0) {
log(IStatus.ERROR, "Cannot find aspect bundle "+aspectBinding.aspectPlugin);
continue;
}
Bundle aspectBundle = aspectBundles[0];
if (shouldScan())
scanTeamClasses(aspectBundle, aspectBinding);
TeamLoader loading = new TeamLoader(deferredTeamClasses);
if (loading.loadTeams(aspectBundle, aspectBinding, className))
// aspectBinding.activated = true; // FIXME(SH): this still spoils team activation, the given class may not be the trigger
;
}
if (!deferredTeamClasses.isEmpty())
aspectBindingRegistry.addDeferredTeamClasses(deferredTeamClasses);
}
}
private synchronized boolean shouldScan() {
boolean shouldScan = !teamsScanned;
teamsScanned = true;
return shouldScan;
}
/** Read OT attributes of all teams in aspectBinding and collect affected base classes. */
private void scanTeamClasses(Bundle bundle, AspectBinding aspectBinding) {
List<String> allTeams = aspectBinding.getAllTeams();
ClassScanner scanner = new ClassScanner();
for (String teamName : allTeams) {
try {
teamName = scanner.readOTAttributes(bundle, teamName);
aspectBinding.addBaseClassNames(teamName, scanner.getCollectedBaseClassNames());
} catch (Exception e) {
log(e, "Failed to load team class "+teamName);
}
}
}
}