Package org.springframework.roo.addon.jsf

Source Code of org.springframework.roo.addon.jsf.JsfOperationsImpl

package org.springframework.roo.addon.jsf;

import static org.springframework.roo.model.RooJavaType.ROO_JSF_CONVERTER;
import static org.springframework.roo.model.RooJavaType.ROO_JSF_MANAGED_BEAN;
import static org.springframework.roo.model.RooJavaType.ROO_SERIALIZABLE;

import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.lang.reflect.Modifier;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.logging.Level;

import org.apache.commons.io.IOUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.Validate;
import org.apache.felix.scr.annotations.Component;
import org.apache.felix.scr.annotations.Reference;
import org.apache.felix.scr.annotations.Service;
import org.springframework.roo.addon.jsf.managedbean.JsfManagedBeanMetadata;
import org.springframework.roo.addon.plural.PluralMetadata;
import org.springframework.roo.classpath.PhysicalTypeCategory;
import org.springframework.roo.classpath.PhysicalTypeIdentifier;
import org.springframework.roo.classpath.TypeLocationService;
import org.springframework.roo.classpath.TypeManagementService;
import org.springframework.roo.classpath.customdata.CustomDataKeys;
import org.springframework.roo.classpath.details.ClassOrInterfaceTypeDetails;
import org.springframework.roo.classpath.details.ClassOrInterfaceTypeDetailsBuilder;
import org.springframework.roo.classpath.details.annotations.AnnotationMetadataBuilder;
import org.springframework.roo.classpath.operations.AbstractOperations;
import org.springframework.roo.metadata.MetadataDependencyRegistry;
import org.springframework.roo.metadata.MetadataService;
import org.springframework.roo.model.JavaPackage;
import org.springframework.roo.model.JavaSymbolName;
import org.springframework.roo.model.JavaType;
import org.springframework.roo.model.RooJavaType;
import org.springframework.roo.project.Dependency;
import org.springframework.roo.project.FeatureNames;
import org.springframework.roo.project.LogicalPath;
import org.springframework.roo.project.Path;
import org.springframework.roo.project.PathResolver;
import org.springframework.roo.project.ProjectOperations;
import org.springframework.roo.project.ProjectType;
import org.springframework.roo.project.Repository;
import org.springframework.roo.project.maven.Pom;
import org.springframework.roo.shell.Shell;
import org.springframework.roo.support.util.DomUtils;
import org.springframework.roo.support.util.FileUtils;
import org.springframework.roo.support.util.WebXmlUtils;
import org.springframework.roo.support.util.XmlElementBuilder;
import org.springframework.roo.support.util.XmlUtils;
import org.w3c.dom.Document;
import org.w3c.dom.Element;

/**
* Implementation of {@link JsfOperations}.
*
* @author Alan Stewart
* @since 1.2.0
*/
@Component
@Service
public class JsfOperationsImpl extends AbstractOperations implements
        JsfOperations {

    private static final String DEPENDENCY_XPATH = "/dependencies/dependency";
    private static final String JSF_IMPLEMENTATION_XPATH = "/configuration/jsf-implementations/jsf-implementation";
    private static final String JSF_LIBRARY_XPATH = "/configuration/jsf-libraries/jsf-library";
    private static final String MYFACES_LISTENER = "org.apache.myfaces.webapp.StartupServletContextListener";
    private static final String MOJARRA_LISTENER = "com.sun.faces.config.ConfigureListener";
    private static final String PRIMEFACES_THEMES_VERSION = "1.0.10";
    private static final String REPOSITORY_XPATH = "/repositories/repository";

    @Reference private MetadataDependencyRegistry metadataDependencyRegistry;
    @Reference private MetadataService metadataService;
    @Reference private PathResolver pathResolver;
    @Reference private ProjectOperations projectOperations;
    @Reference private Shell shell;
    @Reference private TypeLocationService typeLocationService;
    @Reference private TypeManagementService typeManagementService;

    public void addMediaSuurce(final String url, MediaPlayer mediaPlayer) {
        Validate.notBlank(url, "Media source url required");

        final String mainPage = projectOperations.getPathResolver()
                .getFocusedIdentifier(Path.SRC_MAIN_WEBAPP, "pages/main.xhtml");
        final Document document = XmlUtils.readXml(fileManager
                .getInputStream(mainPage));
        final Element root = document.getDocumentElement();
        final Element element = DomUtils
                .findFirstElementByName("p:panel", root);
        if (element == null) {
            return;
        }

        if (mediaPlayer == null) {
            mp: for (final MediaPlayer mp : MediaPlayer.values()) {
                for (final String mediaType : mp.getMediaTypes()) {
                    if (StringUtils.lowerCase(url).contains(mediaType)) {
                        mediaPlayer = mp;
                        break mp;
                    }
                }
            }
        }

        if (url.contains("youtube")) {
            mediaPlayer = MediaPlayer.FLASH;
        }

        final Element paraElement = new XmlElementBuilder("p", document)
                .build();
        Element mediaElement;
        if (mediaPlayer == null) {
            mediaElement = new XmlElementBuilder("p:media", document)
                    .addAttribute("value", url).build();
        }
        else {
            mediaElement = new XmlElementBuilder("p:media", document)
                    .addAttribute("value", url)
                    .addAttribute("player",
                            StringUtils.lowerCase(mediaPlayer.name())).build();
        }
        paraElement.appendChild(mediaElement);
        element.appendChild(paraElement);

        fileManager.createOrUpdateTextFileIfRequired(mainPage,
                XmlUtils.nodeToString(document), false);
    }

    private void addOrRemoveListener(final JsfImplementation jsfImplementation,
            final Document document) {
        Validate.notNull(jsfImplementation, "JSF implementation required");
        Validate.notNull(document, "web.xml document required");

        final Element root = document.getDocumentElement();
        final Element webAppElement = XmlUtils.findFirstElement("/web-app",
                root);
        Element listenerElement;
        switch (jsfImplementation) {
        case ORACLE_MOJARRA:
            listenerElement = XmlUtils.findFirstElement(
                    "listener[listener-class = '" + MYFACES_LISTENER + "']",
                    webAppElement);
            if (listenerElement != null) {
                webAppElement.removeChild(listenerElement);
                DomUtils.removeTextNodes(webAppElement);
            }
            listenerElement = XmlUtils.findFirstElement(
                    "listener[listener-class = '" + MOJARRA_LISTENER + "']",
                    webAppElement);
            if (listenerElement == null) {
                WebXmlUtils.addListener(MOJARRA_LISTENER, document, "");
                DomUtils.removeTextNodes(webAppElement);
            }
            break;
        case APACHE_MYFACES:
            listenerElement = XmlUtils.findFirstElement(
                    "listener[listener-class = '" + MOJARRA_LISTENER + "']",
                    webAppElement);
            if (listenerElement != null) {
                webAppElement.removeChild(listenerElement);
                DomUtils.removeTextNodes(webAppElement);
            }
            listenerElement = XmlUtils.findFirstElement(
                    "listener[listener-class = '" + MYFACES_LISTENER + "']",
                    webAppElement);
            if (listenerElement == null) {
                WebXmlUtils.addListener(MYFACES_LISTENER, document, "");
                DomUtils.removeTextNodes(webAppElement);
            }
            break;
        }
    }

    private void changePrimeFacesTheme(final Theme theme,
            final Document document) {
        Validate.notNull(theme, "Theme required");
        Validate.notNull(document, "web.xml document required");

        // Add theme to the pom if not already there
        final String themeName = StringUtils.lowerCase(theme.name().replace(
                "_", "-"));
        projectOperations.addDependency(
                projectOperations.getFocusedModuleName(),
                "org.primefaces.themes", themeName, PRIMEFACES_THEMES_VERSION);

        // Update the web.xml primefaces.THEME content-param
        final Element root = document.getDocumentElement();

        final Element contextParamElement = XmlUtils
                .findFirstElement(
                        "/web-app/context-param[param-name = 'primefaces.THEME']",
                        root);
        Validate.notNull(contextParamElement,
                "The web.xml primefaces.THEME context param element required");
        final Element paramValueElement = XmlUtils.findFirstElement(
                "param-value", contextParamElement);
        Validate.notNull(paramValueElement,
                "primefaces.THEME param-value element required");
        paramValueElement.setTextContent(themeName);
    }

    private void copyEntityTypePage(final JavaType entity,
            final String beanName, final String plural) {
        final String domainTypeFile = projectOperations.getPathResolver()
                .getFocusedIdentifier(
                        Path.SRC_MAIN_WEBAPP,
                        "pages/"
                                + JavaSymbolName
                                        .getReservedWordSafeName(entity)
                                + ".xhtml");
        InputStream inputStream = null;
        try {
            inputStream = FileUtils.getInputStream(getClass(),
                    "pages/content-template.xhtml");
            String input = IOUtils.toString(inputStream);
            input = input.replace("__BEAN_NAME__", beanName);
            input = input
                    .replace("__DOMAIN_TYPE__", entity.getSimpleTypeName());
            input = input.replace("__LC_DOMAIN_TYPE__", JavaSymbolName
                    .getReservedWordSafeName(entity).getSymbolName());
            input = input.replace("__DOMAIN_TYPE_PLURAL__", plural);

            fileManager.createOrUpdateTextFileIfRequired(domainTypeFile, input,
                    false);
        }
        catch (final IOException e) {
            throw new IllegalStateException("Unable to create '"
                    + domainTypeFile + "'", e);
        }
        finally {
            IOUtils.closeQuietly(inputStream);
        }
    }

    private void createConverter(final JavaPackage javaPackage,
            final JavaType entity) {
        // Create type annotation for new converter class
        final JavaType converterType = new JavaType(
                javaPackage.getFullyQualifiedPackageName() + "."
                        + entity.getSimpleTypeName() + "Converter");
        final AnnotationMetadataBuilder annotationBuilder = new AnnotationMetadataBuilder(
                ROO_JSF_CONVERTER);
        annotationBuilder.addClassAttribute("entity", entity);
        final String declaredByMetadataId = PhysicalTypeIdentifier
                .createIdentifier(converterType,
                        pathResolver.getFocusedPath(Path.SRC_MAIN_JAVA));
        final ClassOrInterfaceTypeDetailsBuilder cidBuilder = new ClassOrInterfaceTypeDetailsBuilder(
                declaredByMetadataId, Modifier.PUBLIC, converterType,
                PhysicalTypeCategory.CLASS);
        cidBuilder.addAnnotation(annotationBuilder);
        cidBuilder.addImplementsType(JsfJavaType.CONVERTER);

        typeManagementService.createOrUpdateTypeOnDisk(cidBuilder.build());

        shell.flash(Level.FINE,
                "Created " + converterType.getFullyQualifiedTypeName(),
                JsfOperationsImpl.class.getName());
        shell.flash(Level.FINE, "", JsfOperationsImpl.class.getName());
    }

    public void createManagedBean(final JavaType managedBean,
            final JavaType entity, String beanName, final boolean includeOnMenu) {
        final JavaPackage managedBeanPackage = managedBean.getPackage();
        installFacesConfig(managedBeanPackage);
        installI18n(managedBeanPackage);
        installBean("ApplicationBean-template.java", managedBeanPackage);

        final String managedBeanTypeName = managedBeanPackage
                .getFullyQualifiedPackageName();
        final JavaPackage utilPackage = new JavaPackage(managedBeanTypeName
                + ".util");
        installBean("LocaleBean-template.java", utilPackage);
        installBean(
                "ViewExpiredExceptionExceptionHandlerFactory-template.java",
                utilPackage);
        installBean("ViewExpiredExceptionExceptionHandler-template.java",
                utilPackage);
        installBean("MessageFactory-template.java", utilPackage);

        if (fileManager.exists(typeLocationService
                .getPhysicalTypeCanonicalPath(managedBean,
                        pathResolver.getFocusedPath(Path.SRC_MAIN_JAVA)))) {
            // Type exists already - nothing to do
            return;
        }

        final ClassOrInterfaceTypeDetails entityTypeDetails = typeLocationService
                .getTypeDetails(entity);
        Validate.notNull(entityTypeDetails,
                "The type '%s' could not be resolved", entity);

        final PluralMetadata pluralMetadata = (PluralMetadata) metadataService
                .get(PluralMetadata.createIdentifier(entity,
                        PhysicalTypeIdentifier.getPath(entityTypeDetails
                                .getDeclaredByMetadataId())));
        Validate.notNull(pluralMetadata,
                "The plural for type '%s' could not be resolved", entity);

        // Create type annotation for new managed bean
        final AnnotationMetadataBuilder annotationBuilder = new AnnotationMetadataBuilder(
                ROO_JSF_MANAGED_BEAN);
        annotationBuilder.addClassAttribute("entity", entity);

        if (StringUtils.isBlank(beanName)) {
            beanName = StringUtils
                    .uncapitalize(managedBean.getSimpleTypeName());
        }
        annotationBuilder.addStringAttribute("beanName", beanName);

        if (!includeOnMenu) {
            annotationBuilder.addBooleanAttribute("includeOnMenu",
                    includeOnMenu);
        }

        final LogicalPath managedBeanPath = pathResolver
                .getFocusedPath(Path.SRC_MAIN_JAVA);
        final String resourceIdentifier = typeLocationService
                .getPhysicalTypeCanonicalPath(managedBean, managedBeanPath);
        final String declaredByMetadataId = PhysicalTypeIdentifier
                .createIdentifier(managedBean,
                        pathResolver.getPath(resourceIdentifier));

        final ClassOrInterfaceTypeDetailsBuilder cidBuilder = new ClassOrInterfaceTypeDetailsBuilder(
                declaredByMetadataId, Modifier.PUBLIC, managedBean,
                PhysicalTypeCategory.CLASS);
        cidBuilder
                .addAnnotation(new AnnotationMetadataBuilder(ROO_SERIALIZABLE));
        cidBuilder.addAnnotation(annotationBuilder);

        typeManagementService.createOrUpdateTypeOnDisk(cidBuilder.build());

        shell.flash(Level.FINE,
                "Created " + managedBean.getFullyQualifiedTypeName(),
                JsfOperationsImpl.class.getName());
        shell.flash(Level.FINE, "", JsfOperationsImpl.class.getName());

        copyEntityTypePage(entity, beanName, pluralMetadata.getPlural());

        // Create a javax.faces.convert.Converter class for the entity
        createConverter(new JavaPackage(managedBeanTypeName + ".converter"),
                entity);
    }

    private void createOrUpdateWebXml(
            final JsfImplementation jsfImplementation, final Theme theme) {
        final String webXmlPath = getWebXmlFile();

        final Document document;
        if (fileManager.exists(webXmlPath)) {
            document = XmlUtils.readXml(fileManager.getInputStream(webXmlPath));
        }
        else {
            document = getDocumentTemplate("WEB-INF/web-template.xml");
            final String projectName = projectOperations.getFocusedModule()
                    .getDisplayName();
            WebXmlUtils.setDisplayName(projectName, document, null);
            WebXmlUtils.setDescription("Roo generated " + projectName
                    + " application", document, null);
        }

        if (jsfImplementation != null) {
            addOrRemoveListener(jsfImplementation, document);
        }
        if (theme != null) {
            changePrimeFacesTheme(theme, document);
        }

        fileManager.createOrUpdateTextFileIfRequired(webXmlPath,
                XmlUtils.nodeToString(document), false);
    }

    public void generateAll(final JavaPackage destinationPackage) {
        Validate.notNull(destinationPackage, "Destination package required");

        // Create JSF managed bean for each entity
        generateManagedBeans(destinationPackage);
    }

    private void generateManagedBeans(final JavaPackage destinationPackage) {
        for (final ClassOrInterfaceTypeDetails cid : typeLocationService
                .findClassesOrInterfaceDetailsWithTag(CustomDataKeys.PERSISTENT_TYPE)) {
            if (Modifier.isAbstract(cid.getModifier())) {
                continue;
            }

            final JavaType entity = cid.getName();
            final LogicalPath path = PhysicalTypeIdentifier.getPath(cid
                    .getDeclaredByMetadataId());

            // Check to see if this persistent type has a JSF metadata listening
            // to it
            final String downstreamJsfMetadataId = JsfManagedBeanMetadata
                    .createIdentifier(entity, path);
            if (metadataDependencyRegistry.getDownstream(
                    cid.getDeclaredByMetadataId()).contains(
                    downstreamJsfMetadataId)) {
                // There is already a JSF managed bean for this entity
                continue;
            }

            // To get here, there is no listening managed bean, so add one
            final JavaType managedBean = new JavaType(
                    destinationPackage.getFullyQualifiedPackageName() + "."
                            + entity.getSimpleTypeName() + "Bean");
            final String beanName = StringUtils.uncapitalize(managedBean
                    .getSimpleTypeName());
            createManagedBean(managedBean, entity, beanName, true);
        }
    }

    private List<Dependency> getDependencies(final String xPathExpression,
            final Element configuration) {
        final List<Dependency> dependencies = new ArrayList<Dependency>();
        for (final Element dependencyElement : XmlUtils.findElements(
                xPathExpression + DEPENDENCY_XPATH, configuration)) {
            dependencies.add(new Dependency(dependencyElement));
        }
        return dependencies;
    }

    private JsfImplementation getExistingOrDefaultJsfImplementation(
            final Element configuration) {
        final Pom pom = projectOperations
                .getPomFromModuleName(projectOperations.getFocusedModuleName());
        JsfImplementation existingJsfImplementation = null;
        for (final JsfImplementation value : JsfImplementation.values()) {
            final Element jsfDependencyElement = XmlUtils.findFirstElement(
                    JSF_IMPLEMENTATION_XPATH + "[@id = '" + value.name() + "']"
                            + DEPENDENCY_XPATH, configuration);
            if (jsfDependencyElement != null
                    && pom.isDependencyRegistered(new Dependency(
                            jsfDependencyElement))) {
                existingJsfImplementation = value;
                break;
            }
        }
        return existingJsfImplementation == null ? JsfImplementation.ORACLE_MOJARRA
                : existingJsfImplementation;
    }

    private JsfLibrary getExistingOrDefaultJsfLibrary(
            final Element configuration) {
        final Pom pom = projectOperations
                .getPomFromModuleName(projectOperations.getFocusedModuleName());
        JsfLibrary existingJsfImplementation = null;
        for (final JsfLibrary value : JsfLibrary.values()) {
            final Element jsfDependencyElement = XmlUtils.findFirstElement(
                    JSF_LIBRARY_XPATH + "[@id = '" + value.name() + "']"
                            + DEPENDENCY_XPATH, configuration);
            if (jsfDependencyElement != null
                    && pom.isDependencyRegistered(new Dependency(
                            jsfDependencyElement))) {
                existingJsfImplementation = value;
                break;
            }
        }
        return existingJsfImplementation == null ? JsfLibrary.PRIMEFACES
                : existingJsfImplementation;
    }

    private String getFacesConfigFile() {
        return projectOperations.getPathResolver().getFocusedIdentifier(
                Path.SRC_MAIN_WEBAPP, "WEB-INF/faces-config.xml");
    }

    private String getJsfImplementationXPath(
            final List<JsfImplementation> jsfImplementations) {
        final StringBuilder builder = new StringBuilder(
                JSF_IMPLEMENTATION_XPATH).append("[");
        for (int i = 0; i < jsfImplementations.size(); i++) {
            if (i > 0) {
                builder.append(" or ");
            }
            builder.append("@id = '");
            builder.append(jsfImplementations.get(i).name());
            builder.append("'");
        }
        builder.append("]");
        return builder.toString();
    }

    private String getJsfLibraryXPath(final List<JsfLibrary> jsfLibraries) {
        final StringBuilder builder = new StringBuilder(JSF_LIBRARY_XPATH)
                .append("[");
        for (int i = 0; i < jsfLibraries.size(); i++) {
            if (i > 0) {
                builder.append(" or ");
            }
            builder.append("@id = '");
            builder.append(jsfLibraries.get(i).name());
            builder.append("'");
        }
        builder.append("]");
        return builder.toString();
    }

    public String getName() {
        return FeatureNames.JSF;
    }

    private List<JsfImplementation> getUnwantedJsfImplementations(
            final JsfImplementation jsfImplementation) {
        final List<JsfImplementation> unwantedJsfImplementations = new ArrayList<JsfImplementation>(
                Arrays.asList(JsfImplementation.values()));
        unwantedJsfImplementations.remove(jsfImplementation);
        return unwantedJsfImplementations;
    }

    private List<JsfLibrary> getUnwantedJsfLibraries(final JsfLibrary jsfLibrary) {
        final List<JsfLibrary> unwantedJsfLibraries = new ArrayList<JsfLibrary>(
                Arrays.asList(JsfLibrary.values()));
        unwantedJsfLibraries.remove(jsfLibrary);
        return unwantedJsfLibraries;
    }

    private String getWebXmlFile() {
        return projectOperations.getPathResolver().getFocusedIdentifier(
                Path.SRC_MAIN_WEBAPP, "WEB-INF/web.xml");
    }

    private boolean hasFacesConfig() {
        return fileManager.exists(getFacesConfigFile());
    }

    private void installBean(final String templateName,
            final JavaPackage destinationPackage) {
        final String beanName = templateName.substring(0,
                templateName.indexOf("-template"));
        final JavaType javaType = new JavaType(
                destinationPackage.getFullyQualifiedPackageName() + "."
                        + beanName);
        final String physicalTypeIdentifier = PhysicalTypeIdentifier
                .createIdentifier(javaType,
                        pathResolver.getFocusedPath(Path.SRC_MAIN_JAVA));
        final String physicalPath = typeLocationService
                .getPhysicalTypeCanonicalPath(physicalTypeIdentifier);
        if (fileManager.exists(physicalPath)) {
            return;
        }

        InputStream inputStream = null;
        try {
            inputStream = FileUtils.getInputStream(getClass(), templateName);
            String input = IOUtils.toString(inputStream);
            input = input.replace("__PACKAGE__",
                    destinationPackage.getFullyQualifiedPackageName());
            fileManager.createOrUpdateTextFileIfRequired(physicalPath, input,
                    false);

            shell.flash(Level.FINE,
                    "Created " + javaType.getFullyQualifiedTypeName(),
                    JsfOperationsImpl.class.getName());
            shell.flash(Level.FINE, "", JsfOperationsImpl.class.getName());
        }
        catch (final IOException e) {
            throw new IllegalStateException("Unable to create '" + physicalPath
                    + "'", e);
        }
        finally {
            IOUtils.closeQuietly(inputStream);
        }
    }

    private void installFacesConfig(final JavaPackage destinationPackage) {
        Validate.isTrue(projectOperations.isFocusedProjectAvailable(),
                "Project metadata required");
        if (hasFacesConfig()) {
            return;
        }

        InputStream inputStream = null;
        try {
            inputStream = FileUtils.getInputStream(getClass(),
                    "WEB-INF/faces-config-template.xml");
            String input = IOUtils.toString(inputStream);
            input = input.replace("__PACKAGE__",
                    destinationPackage.getFullyQualifiedPackageName());
            fileManager.createOrUpdateTextFileIfRequired(getFacesConfigFile(),
                    input, false);
        }
        catch (final IOException e) {
            throw new IllegalStateException(
                    "Unable to create 'faces.config.xml'", e);
        }
        finally {
            IOUtils.closeQuietly(inputStream);
        }
    }

    private void installI18n(final JavaPackage destinationPackage) {
        final String packagePath = destinationPackage
                .getFullyQualifiedPackageName()
                .replace('.', File.separatorChar);
        final String i18nDirectory = projectOperations.getPathResolver()
                .getFocusedIdentifier(Path.SRC_MAIN_RESOURCES,
                        packagePath + "/i18n");
        copyDirectoryContents("i18n/*.properties", i18nDirectory, false);
    }

    public boolean isInstalledInModule(final String moduleName) {
        final LogicalPath webAppPath = LogicalPath.getInstance(
                Path.SRC_MAIN_WEBAPP, moduleName);
        return fileManager.exists(pathResolver.getIdentifier(webAppPath,
                "WEB-INF/faces-config.xml"))
                || fileManager.exists(pathResolver.getIdentifier(webAppPath,
                        "templates/layout.xhtml"));
    }

    public boolean isJsfInstallationPossible() {
        return projectOperations.isFocusedProjectAvailable()
                && !projectOperations
                        .isFeatureInstalledInFocusedModule(FeatureNames.MVC);
    }

    public boolean isScaffoldOrMediaAdditionAvailable() {
        return isInstalledInModule(projectOperations.getFocusedModuleName())
                && fileManager.exists(getWebXmlFile());
    }

    public void setup(JsfImplementation jsfImplementation,
            final JsfLibrary jsfLibrary, final Theme theme) {
        jsfImplementation = updateConfiguration(jsfImplementation, jsfLibrary);
        createOrUpdateWebXml(jsfImplementation, theme);

        final LogicalPath webappPath = Path.SRC_MAIN_WEBAPP
                .getModulePathId(projectOperations.getFocusedModuleName());
        copyDirectoryContents("index.html",
                pathResolver.getIdentifier(webappPath, ""), false);
        copyDirectoryContents("viewExpired.xhtml",
                pathResolver.getIdentifier(webappPath, ""), false);
        copyDirectoryContents("resources/images/*.*",
                pathResolver.getIdentifier(webappPath, "resources/images"),
                false);
        copyDirectoryContents("resources/css/*.css",
                pathResolver.getIdentifier(webappPath, "resources/css"), false);
        copyDirectoryContents("resources/js/*.js",
                pathResolver.getIdentifier(webappPath, "resources/js"), false);
        copyDirectoryContents("templates/*.xhtml",
                pathResolver.getIdentifier(webappPath, "templates"), false);
        copyDirectoryContents("pages/main.xhtml",
                pathResolver.getIdentifier(webappPath, "pages"), false);

        projectOperations.updateProjectType(
                projectOperations.getFocusedModuleName(), ProjectType.WAR);

        fileManager.scan();
    }

    private JsfImplementation updateConfiguration(
            JsfImplementation jsfImplementation, JsfLibrary jsfLibrary) {
        // Update pom.xml with JSF/Primefaces dependencies and repositories
        final Element configuration = XmlUtils.getConfiguration(getClass());

        if (jsfImplementation == null) {
            // JSF implementation was not specified by user so first query POM
            // to determine if there is an existing JSF dependency and use it,
            // otherwise default to Oracle Mojarra
            jsfImplementation = getExistingOrDefaultJsfImplementation(configuration);
        }

        if (jsfLibrary == null) {
            // JSF component libraru was not specified by user so first query
            // POM to determine if there is an existing JSF dependency and use
            // it, otherwise default to PrimeFaces
            jsfLibrary = getExistingOrDefaultJsfLibrary(configuration);
        }

        updateDependencies(configuration, jsfImplementation, jsfLibrary);
        updateRepositories(configuration, jsfImplementation, jsfLibrary);
        return jsfImplementation;
    }

    private void updateDependencies(final Element configuration,
            final JsfImplementation jsfImplementation,
            final JsfLibrary jsfLibrary) {
        final List<Dependency> requiredDependencyElements = new ArrayList<Dependency>();

        final List<Element> jsfImplementationDependencyElements = XmlUtils
                .findElements(jsfImplementation.getConfigPrefix()
                        + DEPENDENCY_XPATH, configuration);
        for (final Element dependencyElement : jsfImplementationDependencyElements) {
            requiredDependencyElements.add(new Dependency(dependencyElement));
        }

        final List<Element> jsfLibraryDependencyElements = XmlUtils
                .findElements(jsfLibrary.getConfigPrefix() + DEPENDENCY_XPATH,
                        configuration);
        for (final Element dependencyElement : jsfLibraryDependencyElements) {
            requiredDependencyElements.add(new Dependency(dependencyElement));
        }

        final List<Element> jsfDependencyElements = XmlUtils.findElements(
                "/configuration/jsf" + DEPENDENCY_XPATH, configuration);
        for (final Element dependencyElement : jsfDependencyElements) {
            requiredDependencyElements.add(new Dependency(dependencyElement));
        }

        // Remove redundant dependencies
        final List<Dependency> redundantDependencyElements = new ArrayList<Dependency>();

        final List<JsfImplementation> unwantedJsfImplementations = getUnwantedJsfImplementations(jsfImplementation);
        if (!unwantedJsfImplementations.isEmpty()) {
            redundantDependencyElements.addAll(getDependencies(
                    getJsfImplementationXPath(unwantedJsfImplementations),
                    configuration));
        }

        final List<JsfLibrary> unwantedJsfLibraries = getUnwantedJsfLibraries(jsfLibrary);
        if (!unwantedJsfLibraries.isEmpty()) {
            redundantDependencyElements.addAll(getDependencies(
                    getJsfLibraryXPath(unwantedJsfLibraries), configuration));
        }

        // Don't remove any we actually need
        redundantDependencyElements.removeAll(requiredDependencyElements);

        // Update the POM
        projectOperations.addDependencies(
                projectOperations.getFocusedModuleName(),
                requiredDependencyElements);
        projectOperations.removeDependencies(
                projectOperations.getFocusedModuleName(),
                redundantDependencyElements);
    }

    private void updateRepositories(final Element configuration,
            final JsfImplementation jsfImplementation,
            final JsfLibrary jsfLibrary) {
        final List<Repository> repositories = new ArrayList<Repository>();

        final List<Element> jsfRepositoryElements = XmlUtils.findElements(
                jsfImplementation.getConfigPrefix() + REPOSITORY_XPATH,
                configuration);
        for (final Element repositoryElement : jsfRepositoryElements) {
            repositories.add(new Repository(repositoryElement));
        }

        final List<Element> jsfLibraryRepositoryElements = XmlUtils
                .findElements(jsfLibrary.getConfigPrefix() + REPOSITORY_XPATH,
                        configuration);
        for (final Element repositoryElement : jsfLibraryRepositoryElements) {
            repositories.add(new Repository(repositoryElement));
        }

        projectOperations.addRepositories(
                projectOperations.getFocusedModuleName(), repositories);
    }
}
TOP

Related Classes of org.springframework.roo.addon.jsf.JsfOperationsImpl

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.