com.abiquo.nodecollector.domain.collectors.VirtualBoxCollector.java Source code

Java tutorial

Introduction

Here is the source code for com.abiquo.nodecollector.domain.collectors.VirtualBoxCollector.java

Source

/**
 * Abiquo community edition
 * cloud management application for hybrid clouds
 * Copyright (C) 2008-2010 - Abiquo Holdings S.L.
 *
 * This application is free software; you can redistribute it and/or
 * modify it under the terms of the GNU LESSER GENERAL PUBLIC
 * LICENSE as published by the Free Software Foundation under
 * version 3 of the License
 *
 * This software is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * LESSER GENERAL PUBLIC LICENSE v.3 for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the
 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
 * Boston, MA 02111-1307, USA.
 */

package com.abiquo.nodecollector.domain.collectors;

import java.io.StringReader;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

import org.apache.commons.lang.StringUtils;
import org.apache.wink.common.internal.providers.entity.csv.CsvReader;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.virtualbox_4_0.DeviceType;
import org.virtualbox_4_0.IHost;
import org.virtualbox_4_0.IHostNetworkInterface;
import org.virtualbox_4_0.IMachine;
import org.virtualbox_4_0.IMedium;
import org.virtualbox_4_0.IMediumAttachment;
import org.virtualbox_4_0.IVirtualBox;
import org.virtualbox_4_0.MachineState;
import org.virtualbox_4_0.VirtualBoxManager;

import com.abiquo.model.enumerator.HypervisorType;
import com.abiquo.nodecollector.aim.AimCollector;
import com.abiquo.nodecollector.aim.impl.AimCollectorImpl;
import com.abiquo.nodecollector.constants.MessageValues;
import com.abiquo.nodecollector.domain.Collector;
import com.abiquo.nodecollector.exception.CollectorException;
import com.abiquo.nodecollector.exception.ConnectionException;
import com.abiquo.nodecollector.exception.NoManagedException;
import com.abiquo.nodecollector.exception.libvirt.AimException;
import com.abiquo.nodecollector.utils.ResourceComparator;
import com.abiquo.server.core.infrastructure.nodecollector.HostDto;
import com.abiquo.server.core.infrastructure.nodecollector.HostStatusEnumType;
import com.abiquo.server.core.infrastructure.nodecollector.ResourceEnumType;
import com.abiquo.server.core.infrastructure.nodecollector.ResourceType;
import com.abiquo.server.core.infrastructure.nodecollector.VirtualDiskEnumType;
import com.abiquo.server.core.infrastructure.nodecollector.VirtualSystemCollectionDto;
import com.abiquo.server.core.infrastructure.nodecollector.VirtualSystemDto;
import com.abiquo.server.core.infrastructure.nodecollector.VirtualSystemStatusEnumType;

/**
 * Special connection for VirtualBox Hypervisor.
 * 
 * @author jdevesa@abiquo.com
 */
@Collector(type = HypervisorType.VBOX, order = 3)
public class VirtualBoxCollector extends AbstractCollector {
    /** The vbox. */
    private transient IVirtualBox vbox;

    /** The logger. */
    private static final Logger LOGGER = LoggerFactory.getLogger(VirtualBoxCollector.class);

    /** The web session manager object. The root of the vBox Hypervisor WService session. */
    private transient VirtualBoxManager mgr;

    // private long defaultDatastoreSize = 1073741824000L;

    String wsmanuser = "wsman";

    String wsmanpassword = "secret";

    Integer vboxPort = 18083;

    String IDECONTROLLER = "IDESController";

    String SATACONTROLLER = "SATASController";

    /**
     * WsmanCollector
     */
    protected AimCollector aimcollector;

    @Override
    public void connect(final String user, final String password) throws ConnectionException {
        wsmanuser = user;
        wsmanpassword = password;

        try {
            mgr = VirtualBoxManager.createInstance(null);
            mgr.connect("http://" + this.getIpAddress() + ":" + vboxPort, user, password);
            vbox = mgr.getVBox();
        } catch (Exception e) {
            throw new ConnectionException(MessageValues.CONN_EXCP_I, e);
        }

        try {
            aimcollector = new AimCollectorImpl(getIpAddress(), getAimPort());
        } catch (AimException e) {
            throw new ConnectionException(MessageValues.CONN_EXCP_IV, e);
        }

    }

    @Override
    public HostDto getHostInfo() throws CollectorException {

        final Integer MEGABYTE = 1048576;
        try {
            final IHost host = vbox.getHost();

            final HostDto info = new HostDto();

            info.setName("default_vBox_name");
            info.setCpu(host.getProcessorOnlineCount());
            info.setRam(host.getMemorySize() * MEGABYTE);
            info.setInitiatorIQN("iqn.2008-04.com.sun.virtualbox.initiator");

            // Getting interface resources

            List<IHostNetworkInterface> ifaces = host.getNetworkInterfaces();
            List<ResourceType> ifacesResource = new ArrayList<ResourceType>();

            for (IHostNetworkInterface iHostNetworkInterface : ifaces) {
                ResourceType nicResource = new ResourceType();
                nicResource.setAddress(iHostNetworkInterface.getHardwareAddress());
                nicResource.setElementName(iHostNetworkInterface.getName());
                nicResource.setResourceType(ResourceEnumType.NETWORK_INTERFACE);
                ifacesResource.add(nicResource);
            }

            // String diskFolder = vbox.getSystemProperties().getDefaultHardDiskFolder();
            // ResourceType diskResource = new ResourceType();
            // diskResource.setAddress(diskFolder);
            // diskResource.setElementName(diskFolder);
            // diskResource.setResourceType(ResourceEnumType.STORAGE_DISK);
            // diskResource.setUnits(new Long(defaultDatastoreSize));
            // diskResource.setAvailableUnits(new Long(defaultDatastoreSize));

            List<ResourceType> datastores = aimcollector.getDatastores();

            try {
                // [ABICLOUDPREMIUM-345] Node collector mustn't return datastores NFS equal to AM.
                // TODO Depends on [ABICLOUDPREMIUM-365]
                // datastores = removeRepositoryDatastore(datastores, repositoryLocation);

                info.getResources().addAll(datastores);

                checkPhysicalState();
                info.setStatus(HostStatusEnumType.MANAGED);
            } catch (NoManagedException e) {
                info.setStatus(HostStatusEnumType.NOT_MANAGED);
                info.setStatusInfo(e.getMessage());
            }

            Collections.sort(ifacesResource, new ResourceComparator());
            info.getResources().addAll(ifacesResource);
            info.setHypervisor(getHypervisorType().getValue());
            info.setVersion(vbox.getVersion());
            info.setStatus(HostStatusEnumType.MANAGED);

            return info;
        } catch (Throwable e) {
            throw new CollectorException(MessageValues.COLL_VER_NS, e);
        }

    }

    @Override
    public VirtualSystemCollectionDto getVirtualMachines() throws CollectorException {

        final Integer MEGABYTE = 1048576;

        VirtualSystemCollectionDto machines = new VirtualSystemCollectionDto();

        for (IMachine machine : vbox.getMachines()) {
            VirtualSystemDto nextVMachine = new VirtualSystemDto();
            nextVMachine.setName(machine.getName());
            nextVMachine.setVport(getFreePortFromPortsList(machine.getVRDEServer().getVRDEProperty("TCP/Ports")));
            nextVMachine.setCpu(machine.getCPUCount());
            nextVMachine.setUuid(machine.getId());
            nextVMachine.setRam(machine.getMemorySize() * MEGABYTE);
            MachineState state = machine.getState();

            if (state.compareTo(MachineState.Running) == 0) {
                nextVMachine.setStatus(VirtualSystemStatusEnumType.ON);
            } else if (state.compareTo(MachineState.Paused) == 0) {
                nextVMachine.setStatus(VirtualSystemStatusEnumType.PAUSED);
            } else {
                nextVMachine.setStatus(VirtualSystemStatusEnumType.OFF);
            }

            List<IMediumAttachment> mediumAttachments = machine.getMediumAttachments();

            for (IMediumAttachment iMediumAttachment : mediumAttachments) {
                ResourceType newResource = new ResourceType();

                if (iMediumAttachment.getType().compareTo(DeviceType.HardDisk) == 0) {
                    IMedium medium = iMediumAttachment.getMedium();
                    if (medium.getDeviceType().compareTo(DeviceType.HardDisk) == 0) {
                        String formatName = medium.getFormat();
                        if (!"iSCSI".equals(formatName)) {
                            newResource.setResourceType(ResourceEnumType.HARD_DISK);
                            newResource.setAddress(medium.getLocation());
                            newResource.setUnits(medium.getSize().longValue());
                            newResource.setConnection(getDatastoreFromFile(medium.getLocation()));
                            newResource.setResourceSubType(mediumFormatToVirtualDiskEnum(formatName).value());
                        } else {
                            newResource.setAddress("unknown");
                            newResource.setConnection("unknown");
                            if (iMediumAttachment.getController().contains(IDECONTROLLER)) {
                                newResource.setResourceType(ResourceEnumType.HARD_DISK);
                                newResource.setUnits(new Long(0));
                                newResource.setResourceSubType(VirtualDiskEnumType.STATEFUL.value());
                            } else if (iMediumAttachment.getController().contains(SATACONTROLLER)) {
                                newResource.setResourceType(ResourceEnumType.VOLUME_DISK);
                                newResource.setUnits(medium.getSize().longValue());
                                newResource.setResourceSubType(VirtualDiskEnumType.UNKNOWN.value());
                            }
                        }
                    }

                }
                nextVMachine.getResources().add(newResource);
            }

            machines.getVirtualSystems().add(nextVMachine);
        }

        return machines;
    }

    /**
     * Parses the fileName to get the datastore name.
     * 
     * @param fileName the file name to parse
     * @return the datastore directory
     */
    private String getDatastoreFromFile(final String fileName) {
        int count = StringUtils.countMatches(fileName, "/");
        if (count == 1) {
            return "/";
        }
        int indexEndDirectory = fileName.lastIndexOf('/');
        return fileName.substring(0, indexEndDirectory);
    }

    @Override
    public void disconnect() throws CollectorException {
        try {
            mgr.disconnect();
            mgr.cleanup();
        } catch (Exception e) {
            throw new CollectorException(MessageValues.CONN_EXCP_III, e);
        }
    }

    private int getFreePortFromPortsList(final String csvPorts) {
        List<Integer> portList = new ArrayList<Integer>();
        try {
            CsvReader reader = new CsvReader(new StringReader(csvPorts));
            String[] line = reader.readLine();
            if (line != null) {
                for (String port : line) {
                    Integer portInt = Integer.valueOf(port);
                    portList.add(portInt);
                }
            }
        } catch (NumberFormatException e) {
            LOGGER.debug("Ignoring not integer port");
        }

        if (portList.isEmpty()) {
            return -1;
        } else {
            return portList.get(0);
        }
    }

    private VirtualDiskEnumType mediumFormatToVirtualDiskEnum(final String formatId) {
        if ("raw".equals(formatId)) {
            return VirtualDiskEnumType.RAW;
        } else if ("VMDK".equals(formatId)) {
            return VirtualDiskEnumType.VMDK_FLAT;
        } else if ("VDI".equals(formatId)) {
            return VirtualDiskEnumType.VDI_FLAT;
        } else if ("VHD".equals(formatId)) {
            return VirtualDiskEnumType.VHD_FLAT;
        } else {
            return VirtualDiskEnumType.INCOMPATIBLE;
        }
    }

    protected void checkPhysicalState() throws NoManagedException {
        try {
            aimcollector.checkAIM();
        } catch (AimException e) {
            throw new NoManagedException(e.getMessage(), e);
        }
    }

}