alvinalexander.com | career | drupal | java | mac | mysql | perl | scala | uml | unix  

Glassfish example source code file (ImportSyncBundleCommand.java)

This example Glassfish source code file (ImportSyncBundleCommand.java) is included in the DevDaily.com "Java Source Code Warehouse" project. The intent of this project is to help you "Learn Java by Example" TM.

Java - Glassfish tags/keywords

commandexception, commandexception, dashost, dasprotocol, file, file, fileinputstream, instance_dotted_name, io, ioexception, ioexception, log, logging, param, rendezvous_dotted_name, string, string, util, zip

The Glassfish ImportSyncBundleCommand.java source code

/*
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
 *
 * Copyright (c) 2010 Oracle and/or its affiliates. All rights reserved.
 *
 * The contents of this file are subject to the terms of either the GNU
 * General Public License Version 2 only ("GPL") or the Common Development
 * and Distribution License("CDDL") (collectively, the "License").  You
 * may not use this file except in compliance with the License.  You can
 * obtain a copy of the License at
 * https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
 * or packager/legal/LICENSE.txt.  See the License for the specific
 * language governing permissions and limitations under the License.
 *
 * When distributing the software, include this License Header Notice in each
 * file and include the License file at packager/legal/LICENSE.txt.
 *
 * GPL Classpath Exception:
 * Oracle designates this particular file as subject to the "Classpath"
 * exception as provided by Oracle in the GPL Version 2 section of the License
 * file that accompanied this code.
 *
 * Modifications:
 * If applicable, add the following below the License Header, with the fields
 * enclosed by brackets [] replaced by your own identifying information:
 * "Portions Copyright [year] [name of copyright owner]"
 *
 * Contributor(s):
 * If you wish your version of this file to be governed by only the CDDL or
 * only the GPL Version 2, indicate your decision by adding "[Contributor]
 * elects to include this software in this distribution under the [CDDL or GPL
 * Version 2] license."  If you don't indicate a single choice of license, a
 * recipient has the option to distribute your version of this file under
 * either the CDDL, the GPL Version 2 or to extend the choice of license to
 * its licensees as provided above.  However, if you add GPL Version 2 code
 * and therefore, elected the GPL Version 2 license, then the option applies
 * only if the new code is made subject to such option by the copyright
 * holder.
 */

package com.sun.enterprise.admin.cli.cluster;

import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.IOException;

//import java.net.InetAddress;
//import java.net.UnknownHostException;
import java.util.*;
import java.util.logging.Level;
import java.util.zip.ZipEntry;
import java.util.zip.ZipFile;
import javax.xml.stream.XMLInputFactory;
import javax.xml.stream.XMLStreamException;
import javax.xml.stream.XMLStreamReader;
import org.jvnet.hk2.annotations.*;
import org.jvnet.hk2.component.*;
import org.glassfish.api.Param;
import org.glassfish.api.admin.*;
import static com.sun.enterprise.admin.cli.CLIConstants.*;
import com.sun.enterprise.admin.cli.remote.RemoteCommand;
import com.sun.enterprise.util.io.FileUtils;
import java.io.FileInputStream;
import org.glassfish.admin.payload.PayloadImpl;
import org.glassfish.admin.payload.PayloadFilesManager.Perm;

/**
 * This is a local command that unbundles the bundle generated by export-sync-bundle.
 * import-sync-bundle applies the content under ${com.sun.aas.instanceRoot}/
 * directory. Synchronization cookie with DAS's timestamp should be created.
 * It also creates das.properties (if not present) under agent dir (ex.
 * installRoot/glassfish3/glassfish/nodes/<host-name>/agent/config/das.properties).
 *
 * Before running this command the instance should already have been registered in
 * DAS (server element created in DAS domain.xml) by running create-instance.
 * This command does not validate --node or instance_name.
 *
 * For upgrade - this command creates a new instance filesystem if it does not exist.
 * and completes DAS registration by setting rendezvousOccurred=true.
 *
 * For manual sync - this command creates a new instance filesystem or updates the
 * directories of an existing instance (remove existing application, generated,
 * config, docroot, lib dir first and explode the zip) and completes registration with DAS
 * by setting rendezvousOccurred=true.
 *
 * If setting of rendezvousOccurred=true with DAS fails, the command does not
 * not fail. Only a warning is printed out in the command output. We provide the
 * exact "asadmin set command" in this warning so that user can run
 * that command on DAS to change the rendezvousOccurred property for the server instance.
 *
 * Usage:
 *
 * import-sync-bundle [--node node_name] [--nodedir node_path] --file
 * xyz-sync-bundle.zip instance_name
 *
 * --node         name of the node; this is optional. The command fails if there
 * is more than one node under the default location
 * (installRoot/glassfish3/glassfish/nodes/<host-name>/)
 *
 * --nodedir      parent dir where node is created; this is optional. Default
 * location is installRoot/glassfish3/glassfish/nodes/
 *
 * --file         sync bundle created by export-sync-bundle
 *
 * instance_name  name of the server instance
 */
@Service(name = "import-sync-bundle")
@Scoped(PerLookup.class)
public class ImportSyncBundleCommand extends LocalInstanceCommand {
    @Param(name = "file_name", primary = true)
    private String syncBundle;

    @Param(name = "instance")
    private String instanceName0;

    @Param(name = "node", optional = true, alias = "nodeagent")
    protected String _node;

    String DASHost;
    int DASPort = -1;
    String DASProtocol;
    boolean dasIsSecure;

    private File dasPropsFile;
    private Properties dasProperties;

    protected boolean setDasDefaultsOnly = false;
    private File syncBundleFile = null;
    private File agentConfigDir;
    private File backupDir;

    private static final String RENDEZVOUS_PROPERTY_NAME = "rendezvousOccurred";
    private String INSTANCE_DOTTED_NAME;
    private String RENDEZVOUS_DOTTED_NAME;
    //private String RENDEZVOUS_DOTTED_NAME_VALUE;
    //private boolean isDasRunning;

    /**
     */
    @Override
    protected void validate()
            throws CommandException {

        if(ok(instanceName0))
            instanceName = instanceName0;
        else
            throw new CommandException(Strings.get("Instance.badInstanceName"));

        syncBundleFile = new File(syncBundle);
        if (!syncBundleFile.isFile())
            throw new CommandException(Strings.get("noFile", syncBundle));

        if (!isRegisteredToDAS()) {
            throw new CommandException(Strings.get("import.sync.bundle.invalidInstance", instanceName));
        }
        node = _node;

        //isDasRunning = rendezvousWithDAS() ? true : false;

        //Should we validate node and instance if das is running? No validation for now.
        //setDasDefaultsOnly = true; //Issue 12847 - Call super.validate to setDasDefaults only
        //super.validate();          //so _validate-node uses das host from das.properties. No dirs created.

        //init();

        //if (node != null && isDasRunning) {
        //    validateNode(node, getInstallRootPath(), getInstanceHostName(true));
        //}

        //setDasDefaultsOnly = false;
        super.validate(); // set ServerDirs
        init();
    }

    private void init() throws CommandException {
        agentConfigDir = new File(nodeDirChild, "agent" + File.separator + "config");
        dasPropsFile = new File(agentConfigDir, "das.properties");

        if (dasPropsFile.isFile()) {
            setDasDefaults(dasPropsFile);
        }

        DASHost = programOpts.getHost();
        DASPort = programOpts.getPort();
        dasIsSecure = programOpts.isSecure();
        DASProtocol = "http";

        INSTANCE_DOTTED_NAME = "servers.server." + instanceName;
        RENDEZVOUS_DOTTED_NAME = INSTANCE_DOTTED_NAME + ".property." + RENDEZVOUS_PROPERTY_NAME;
        //RENDEZVOUS_DOTTED_NAME_VALUE = RENDEZVOUS_DOTTED_NAME + "=true";
    }

    private boolean isRegisteredToDAS() throws CommandException {
        boolean isRegisteredOnDAS = false;
        InputStream input = null;
        XMLStreamReader reader = null;
        try {
            //find node from domain.xml
            ZipFile zip = new ZipFile(syncBundleFile);
            ZipEntry entry = zip.getEntry("config/domain.xml");
            if (entry != null) {
                input = zip.getInputStream(entry);

                reader = XMLInputFactory.newInstance().createXMLStreamReader(input);
                while (!isRegisteredOnDAS) {
                    int event = reader.next();

                    if (event == XMLStreamReader.END_DOCUMENT) {
                        break;
                    }

                    if (event == XMLStreamReader.START_ELEMENT && "server".equals(reader.getLocalName())) {
                        // get the attributes for this <server>
                        int num = reader.getAttributeCount();
                        Map<String, String> map = new HashMap();
                        for (int i = 0; i < num; i++) {
                            map.put(reader.getAttributeName(i).getLocalPart(), reader.getAttributeValue(i));
                        }
                        String thisName = map.get("name");
                        if (instanceName.equals(thisName)) {
                            isRegisteredOnDAS = true;
                            if (_node == null) {  // if node not specified
                                _node = map.get("node"); // find it in domain.xml
                            }
                        }
                    }
                }
                if (input != null) input.close();
                if (reader != null) reader.close();
            } else {
                throw new CommandException(Strings.get("import.sync.bundle.domainXmlNotFound",
                    syncBundle));
            }
        } catch (IOException ex) {
            logger.log(Level.SEVERE, Strings.get("import.sync.bundle.inboundPayloadFailed",
                    syncBundle, ex.getLocalizedMessage()), ex);
            throw new CommandException(Strings.get("import.sync.bundle.inboundPayloadFailed",
                    syncBundle, ex.getLocalizedMessage()), ex);
        } catch (XMLStreamException xe) {
            logger.log(Level.SEVERE, Strings.get("import.sync.bundle.inboundPayloadFailed",
                    syncBundle, xe.getLocalizedMessage()), xe);
            throw new CommandException(Strings.get("import.sync.bundle.inboundPayloadFailed",
                    syncBundle, xe.getLocalizedMessage()), xe);
        }

        return isRegisteredOnDAS;
    }

    /**
     */
    @Override
    protected int executeCommand()
            throws CommandException {
            int exitCode = createDirectories();
            if (exitCode == SUCCESS) {
                setRendezvousOccurred("true");
            }
            return exitCode;
    }

    private int createDirectories() throws CommandException {
        if (!agentConfigDir.isDirectory()) {
            agentConfigDir.mkdirs();
        }
        
        writeProperties();
        
        FileInputStream in = null;
        Payload.Inbound payload = null;
        try {
            in = new FileInputStream(syncBundle);
            payload = PayloadImpl.Inbound.newInstance("application/zip", in);
        } catch (IOException ex) {
            try {
                if (in != null) in.close();
            } catch (IOException ioe) {
                logger.warning(Strings.get("import.sync.bundle.closeStreamFailed",
                            syncBundle, ioe.getLocalizedMessage()));
            }
            throw new CommandException(Strings.get("import.sync.bundle.inboundPayloadFailed",
                    syncBundle, ex.getLocalizedMessage()), ex);
        }
        backupInstanceDir();
        File targetDir = this.getServerDirs().getServerDir();
        targetDir.mkdirs();
        Perm perm = new Perm(targetDir, null, logger);

        try {
            perm.processParts(payload);
        } catch (Exception ex) {
            restoreInstanceDir();
            String msg = Strings.get("import.sync.bundle.extractBundleFailed",
                    syncBundle, targetDir.getAbsolutePath());
            if (ex.getLocalizedMessage() != null)
                msg = msg + "\n" + ex.getLocalizedMessage();
            throw new CommandException(msg, ex);
        } finally {
            try {
                if (in != null) in.close();
            } catch (IOException ex) {
                logger.warning(Strings.get("import.sync.bundle.closeStreamFailed",
                            syncBundle, ex.getLocalizedMessage()));
            }
        }
        
        deleteBackupDir();
        return SUCCESS;
    }

    private void writeProperties() throws CommandException {
        try {
            if (!dasPropsFile.isFile()) {
                writeDasProperties();
            }
        } catch (IOException ex) {
            throw new CommandException(Strings.get("Instance.cantWriteProperties", "das.properties", ex.getLocalizedMessage()), ex);
        }
    }

    private void writeDasProperties() throws IOException {
        dasPropsFile.createNewFile();
        dasProperties = new Properties();
        dasProperties.setProperty(K_DAS_HOST, DASHost);
        dasProperties.setProperty(K_DAS_PORT, String.valueOf(DASPort));
        dasProperties.setProperty(K_DAS_IS_SECURE, String.valueOf(dasIsSecure));
        dasProperties.setProperty(K_DAS_PROTOCOL, DASProtocol);

        FileOutputStream fos = new FileOutputStream(dasPropsFile);
        dasProperties.store(fos, Strings.get("Instance.dasPropertyComment"));
        fos.close();
    }

    private void backupInstanceDir() throws CommandException {
        File f = getServerDirs().getServerDir();
        if (f != null && f.isDirectory()) {
            Random r = new Random();
            setBackupDir(r.nextInt());
            File backup = getBackupDir();
            if (!f.renameTo(backup)) {
                logger.warning(Strings.get("import.sync.bundle.backupInstanceDirFailed", f.getAbsolutePath(), backup.getAbsolutePath()));
                if (FileUtils.whack(f)) { //Ask user first before deleting?
                    logger.warning(Strings.get("import.sync.bundle.deletedInstanceDir", f.getAbsolutePath()));
                }
            }

        }
    }

    private void setBackupDir(int i) {
        File f = getServerDirs().getServerDir();
        backupDir = new File(getServerDirs().getServerParentDir(), f.getName() + "_backup" + i);
    }

    private File getBackupDir() {
        return backupDir;
    }

    private void restoreInstanceDir() {
        File backup = getBackupDir();
        if (backup != null && backup.isDirectory()) {
            getServerDirs().getServerDir().delete();
            backup.renameTo(getServerDirs().getServerDir());
        }
    }

    private void deleteBackupDir() {
        File backup = getBackupDir();
        if (backup != null && backup.isDirectory()) {
            FileUtils.whack(backup);
        }
    }

    private void setRendezvousOccurred(String rendezVal) {
        String dottedName = RENDEZVOUS_DOTTED_NAME + "=" + rendezVal;
        try {
            RemoteCommand rc = new RemoteCommand("set", this.programOpts, this.env);
            rc.executeAndReturnOutput("set", dottedName);
        } catch (CommandException ex) {
            logger.warning(Strings.get("import.sync.bundle.completeRegistrationFailed", dottedName));
        }
    }

    /*private boolean rendezvousWithDAS() {
        try {
            getUptime();
            return true;
        } catch (CommandException ex) {
            return false;
        }
    }

    private String getInstanceHostName(boolean isCanonical) throws CommandException {
        String instanceHostName = null;
        InetAddress localHost = null;
        try {
            localHost = InetAddress.getLocalHost();
        } catch (UnknownHostException ex) {
            throw new CommandException(Strings.get("cantGetHostName", ex));
        }
        if (localHost != null) {
            if (isCanonical) {
                instanceHostName = localHost.getCanonicalHostName();
            } else {
                instanceHostName = localHost.getHostName();
            }
        }
        return instanceHostName;
    }

    private int validateNode(String name, String installdir, String nodeHost) throws CommandException {
        ArrayList<String> argsList = new ArrayList();
        argsList.add(0, "_validate-node");

        if (nodeDir != null) {
            argsList.add("--nodedir");
            argsList.add(nodeDir);
        }
        if (nodeHost != null) {
            argsList.add("--nodehost");
            argsList.add(nodeHost);
        }
        if (installdir != null) {
            argsList.add("--installdir");
            argsList.add(installdir);
        }

        argsList.add(name);

        String[] argsArray = new String[argsList.size()];
        argsArray = argsList.toArray(argsArray);

        RemoteCommand rc = new RemoteCommand("_validate-node", this.programOpts, this.env);
        return rc.execute(argsArray);
    }

    private boolean isRegisteredToDAS() {
        boolean isRegistered = true;
        try {
            RemoteCommand rc = new RemoteCommand("get", this.programOpts, this.env);
            rc.executeAndReturnOutput("get", INSTANCE_DOTTED_NAME);
        } catch (CommandException ex) {
            isRegistered = false;
        }
        return isRegistered;
    }

    @Override
    protected boolean mkdirs(File f) {
        if (setDasDefaultsOnly) {
            return true;
        } else {
            return f.mkdirs();
        }
    }

    @Override
    protected boolean isDirectory(File f) {
        if (setDasDefaultsOnly) {
            return true;
        } else {
            return f.isDirectory();
        }
    }

    @Override
    protected boolean setServerDirs() {
        if (setDasDefaultsOnly) {
            return false;
        } else {
            return true;
        }
    }*/

}

Other Glassfish examples (source code examples)

Here is a short list of links related to this Glassfish ImportSyncBundleCommand.java source code file:

... this post is sponsored by my books ...

#1 New Release!

FP Best Seller

 

new blog posts

 

Copyright 1998-2021 Alvin Alexander, alvinalexander.com
All Rights Reserved.

A percentage of advertising revenue from
pages under the /java/jwarehouse URI on this website is
paid back to open source projects.