package org.springframework.roo.addon.cache;
import org.apache.commons.lang3.StringUtils;
import org.apache.felix.scr.annotations.Component;
import org.apache.felix.scr.annotations.Reference;
import org.apache.felix.scr.annotations.Service;
import org.osgi.framework.BundleContext;
import org.osgi.framework.InvalidSyntaxException;
import org.osgi.framework.ServiceReference;
import org.osgi.service.component.ComponentContext;
import org.springframework.roo.addon.cache.providers.CacheProvider;
import org.springframework.roo.shell.CliAvailabilityIndicator;
import org.springframework.roo.shell.CliCommand;
import org.springframework.roo.shell.CliOption;
import org.springframework.roo.shell.CliOptionAutocompleteIndicator;
import org.springframework.roo.shell.CommandMarker;
import org.springframework.roo.shell.ShellContext;
import org.springframework.roo.support.logging.HandlerUtils;
import java.util.ArrayList;
import java.util.List;
import java.util.logging.Logger;
/**
* Commands for the 'cache' add-on to be used by the ROO shell.
*
* This command marker will provide necessary operations to add intermediate
* memory support on generated project.
*
* @author Sergio Clares
* @since 2.0
*/
@Component
@Service
public class CacheCommands implements CommandMarker {
private static final Logger LOGGER = HandlerUtils.getLogger(CacheCommands.class);
//------------ OSGi component attributes ----------------
private BundleContext context;
@Reference
private CacheOperations cacheOperations;
private List<CacheProvider> cacheProviders = new ArrayList<CacheProvider>();
protected void activate(final ComponentContext context) {
this.context = context.getBundleContext();
}
/**
* Method that checks if cache setup operation is available or not.
*
* "cache setup" command will be available only if some project was generated
* and persistence installed.
*
* @return true if some project was created on focused directory and it has
* persistence installed.
*/
@CliAvailabilityIndicator("cache setup")
public boolean isCacheSetupCommandAvailable() {
return cacheOperations.isCacheSetupAvailable();
}
/**
* This indicator returns the cache provider possible values.
*
* @param shellContext
* @return a List<String> with the possible and allowed values.
*/
@CliOptionAutocompleteIndicator(command = "cache setup", param = "provider",
help = "'--provider' value should be a supported provider (GUAVA).")
public List<String> getProviderPossibleValues(ShellContext shellContext) {
List<String> possibleValues = new ArrayList<String>();
for (CacheProvider provider : getCacheProviders()) {
possibleValues.add(provider.getName());
}
return possibleValues;
}
/**
* Method that register "cache setup" command on Spring Roo Shell.
*
* Installs support for intermediate memory. Users can specify different providers
* to use for managing it.
*
* @param provider
* the String with the name of a provider to use for intermediate memory managing.
* @param shellContext
* ShellContext used to know if --force parameter has been used by developer
*
*/
@CliCommand(
value = "cache setup",
help = "Installs support for using intermediate memory in generated project by using Spring Cache abstraction. Users can specify different providers to use for managing it.")
public void cacheSetup(@CliOption(key = "provider", mandatory = false,
help = "Parameter that indicates the provider to use for managing intermediate memory. "
+ "Possible values are: `GUAVA`.") String provider, ShellContext shellContext) {
// Check for provider value
CacheProvider selectedCacheProvider = null;
if (StringUtils.isNotBlank(provider)) {
for (CacheProvider cacheProvider : getCacheProviders()) {
if (provider.equals(cacheProvider.getName())) {
selectedCacheProvider = cacheProvider;
}
}
}
cacheOperations.setupCache(selectedCacheProvider, shellContext.getProfile());
}
/**
* Gets the right implementation of FieldCreatorProvider for a JavaType
*
* @param type the JavaType to get the implementation
* @return FieldCreatorProvider implementation
*/
public List<CacheProvider> getCacheProviders() {
// Get all Services implement FieldCreatorProvider interface
if (cacheProviders.isEmpty()) {
try {
ServiceReference<?>[] references =
this.context.getAllServiceReferences(CacheProvider.class.getName(), null);
for (ServiceReference<?> ref : references) {
CacheProvider cacheProvider = (CacheProvider) this.context.getService(ref);
cacheProviders.add(cacheProvider);
}
} catch (InvalidSyntaxException e) {
LOGGER.warning("Cannot load CacheProvider on CacheCommands.");
return null;
}
}
return cacheProviders;
}
}