<?xml version="1.0" encoding="utf-8"?>
<!--
  - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  - JaDOrT: JASMINe Deployment Orchestration Tool
  - Copyright (C) 2008-2009 Bull S.A.S.
  - Copyright (C) 2008-2009 France Telecom R&D
  - Contact: jasmine@ow2.org
  -
  - This library 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; either
  - version 2.1 of the License, or any later version.
  -
  - This library 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 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
  -
  - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  - $Id: SelectApplication.mxml 4063 2009-06-18 08:15:08Z alitokmen $
  - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
-->
<mx:Canvas xmlns:mx="http://www.adobe.com/2006/mxml"
           xmlns:model="org.ow2.jasmine.jadort.client.flex.model.*"
           xmlns:view="org.ow2.jasmine.jadort.client.flex.view.*"
           width="100%"
           height="100%"
           backgroundColor="#FFFFFF"
           cornerRadius="6"
           updateComplete="clearSelectionBoxes()"
           creationComplete="initApp()">

    <mx:Script>
        <![CDATA[

        import mx.collections.ArrayCollection;
        import mx.controls.Alert;
        import mx.utils.ObjectUtil;
        import flash.events.*;
        import flash.net.FileReference;
        import flash.net.URLRequest;
        import org.ow2.jasmine.jadort.client.flex.model.*;
        import org.ow2.jasmine.jadort.client.flex.view.*;
        import org.ow2.jasmine.jadort.client.flex.vo.*;
        import org.ow2.jasmine.jadort.client.flex.event.*;
        import com.adobe.cairngorm.control.CairngormEventDispatcher;
        import mx.controls.DataGrid;
        import mx.utils.StringUtil;

        private var maxFileSize : Number = 4194304; //bytes;
        private var DeployTypes : FileFilter = new FileFilter("(*.war; *.jar; *.ear)", "*.war; *.jar; *.ear");
        private var allTypes : Array = new Array(DeployTypes);
        private const FILE_UPLOAD_URL : String = "./UploadFileServlet";
        private var fileRef : FileReference;

        [Bindable]
        public var model : JadortModelLocator = JadortModelLocator.getInstance();

        [ArrayElementType(ApplicationVO)]
        private var serverApplications : ArrayCollection; 

        private function clearSelectionBoxes() : void {
            if (progressBar != null && btn_cancel != null && deployType != null) {
                progressBar.setProgress(0, 100);
                progressBar.label = "Click \"Browse\" and select the file to upload...";
                btn_cancel.enabled = false;
                deployType.text = "";
            }

            if (applicationlist != null) {
                serverApplications = new ArrayCollection();
                if (model != null && model.selectedGroup != null) {
                    for each (var server:ServerVO in model.selectedGroup.servers) {
                        for each (var app:ApplicationVO in server.applications) {
                            app.setServerName(server.name);
                            serverApplications.addItem(app);
                        }
                    }
                }
                applicationlist.dataProvider = serverApplications;
                applicationlist.rowCount = serverApplications.length;
            }
        }

        private function initApp() : void {
            fileRef = new FileReference();
            fileRef.addEventListener(ProgressEvent.PROGRESS, progressHandler);
            fileRef.addEventListener(DataEvent.UPLOAD_COMPLETE_DATA, completeHandler);
            fileRef.addEventListener(Event.SELECT, selectHandler);
            fileRef.addEventListener(IOErrorEvent.IO_ERROR, ioErrorHandler);
            fileRef.addEventListener(SecurityErrorEvent.SECURITY_ERROR, securityErrorHandler);
            fileRef.addEventListener(HTTPStatusEvent.HTTP_STATUS, httpStatusHandler);

            CairngormEventDispatcher.getInstance().addEventListener(
                ApplicationSelectedEvent.EVENT_APPLICATION_SELECTED, outputApplicationDetails);
        }

        private function applicationColor(datagrid:DataGrid, rowIndex : int, color : uint) : uint {
            if (datagrid.dataProvider != null) {
                var item:Object = datagrid.dataProvider.getItemAt(rowIndex);
                var value : String = item["name"];

                if (model != null && model.uploadedApplication != null && model.uploadedApplication.name == value) {
                    return 0x87C587;
                }
            }

            return color;
        }

        private function httpStatusHandler(event : HTTPStatusEvent) : void {
            if (event.status != 200) {
                var error : String = "Error " + event.status;
                if (event.status == 500) {
                    error = "Internal server error";
                }
                if (event.status == 404){
                    error = "File not found";
                }
                if (event.status == 415){
                    error = "File type not authorized";
                }
                if (event.status == 401){
                    error = "Access denied";
                }
                Alert.show(error, "HTTP error");
            }
        }

        private function securityErrorHandler(event : SecurityErrorEvent) : void {
            Alert.show(String(event), "Security error");
        }

        private function ioErrorHandler(event : IOErrorEvent) : void {
            Alert.show(String(event), "Input/Output error");
        }

        private function selectHandler(event : Event) : void {
            var msg : String ="";

            try {
                if (checkFileSize(fileRef.size)){
                    btn_upload.enabled = true;
                    progressBar.setProgress(0, 100);
                    progressBar.label = "File selected. Press \"Upload\" to upload it.";
                } else {
                    msg=fileRef.name + " is too large: "+ Math.round(fileRef.size / 1024)+" Kb\n";
                    btn_upload.enabled = false;
                    Alert.show(msg + "Max File Size is: " + Math.round(maxFileSize / 1024) + " kb", "File Too Large",4,null);
                }
            } catch (error : Error) {
                btn_upload.enabled = false;
                Alert.show("File \"" + fileRef.name + "\" cannot be uploaded because it is an empty file.", "Upload Error");
            }
        }

        private function progressHandler(event : ProgressEvent) : void {
            progressBar.setProgress(event.bytesLoaded, event.bytesTotal);
        }

        private function completeHandler(event : DataEvent) : void {
            progressBar.label = "Complete.";
            btn_upload.enabled = false;
            btn_cancel.enabled = false;
            var dataXML:XML = XML(event.data.toString());
            var fileName : String = dataXML.file.attribute('name');
            if (dataXML != null || dataXML.length() <= 0 || fileName != null || fileName != "") {
                Alert.show("The file has successfully uploaded to the server running JaDOrT");
                var createApplicationEvent : CreateApplicationEvent = new CreateApplicationEvent(fileName);
                CairngormEventDispatcher.getInstance().dispatchEvent(createApplicationEvent);
            } else {
                Alert.show("Problem uploading file. Check the server error log for details.");
            }
        }

        private function outputApplicationDetails(event : Event) : void {
            // Careful: applicationDetails and/or deployType not set when loading
            if (applicationDetails != null && deployType != null && serverApplications != null) {
                if (serverApplications == null || model == null ||
                    model.uploadedApplication == null || model.selectedGroup == null) {
                    applicationDetails.text = "(no application uploaded yet)";
                    deployType.text = "";
                } else {
                    var isNewVersion : Boolean = false;
                    applicationDetails.text = model.uploadedApplication.toString();
                    for each (var app:ApplicationVO in serverApplications) {
                        if (app.name == model.uploadedApplication.name) {
                            isNewVersion = true;
                            if (app.version == model.uploadedApplication.version) {
                                Alert.show("WARNING: The version \"" + app.version + "\" of the application \"" + app.name
                                    + "\"  seems to be already deployed! JaDOrT will still let you proceed, but at your own risk.");
                            }
                        }
                    }
                    if (isNewVersion) {
                        deployType.text = "The application that will be deployed is a new version of the application \""
                            + model.uploadedApplication.name + "\" on at least one server";
                    } else {
                        deployType.text = "The application that will be deployed is a new application on all servers";
                    }
                    applicationlist.dataProvider = serverApplications;
                    applicationlist.rowCount = serverApplications.length;
                }
            }
        }

        private function uploadFileFunction() : void {
            var postVariables : URLVariables = new URLVariables;

            var req : URLRequest = new URLRequest;
            req.url = FILE_UPLOAD_URL;
            req.method = URLRequestMethod.POST;
            postVariables.MAX_FILE_SIZE = (32 * 1024 * 1024);
            req.data = postVariables;
            fileRef.upload(req);
            progressBar.label = "Uploading...";
            btn_cancel.enabled = true;
        }

        private function CancelFunction() : void {
            fileRef.cancel()
            clearSelectionBoxes();
        }

        // Checks the files do not exceed maxFileSize | if _maxFileSize == 0 No File Limit Set
        private function checkFileSize(filesize : Number) : Boolean {
            if (maxFileSize == 0){
                return (filesize <= maxFileSize);
            } else {
                return true;
            }
        }

        private function loadUrlFile() : void {
            if (StringUtil.trim(UrlFile.text) == "") {
                mx.controls.Alert.show("URL is empty!");
            } else {
                var createApplicationEvent : CreateApplicationEvent = new CreateApplicationEvent(UrlFile.text);
                CairngormEventDispatcher.getInstance().dispatchEvent(createApplicationEvent);
            }
        }

        ]]>
    </mx:Script>

    <mx:Grid x="0" y="0" width="100%" height="100%" horizontalAlign="center">
        <mx:GridRow width="100%" height="30">
            <mx:GridItem width="100%" height="100%" colSpan="2">
                <mx:Label width="100%" color="blue" text="Upload application to the server running JaDOrT:" height="100%" fontSize="11" />
            </mx:GridItem>
        </mx:GridRow>
        <mx:GridRow width="100%" height="30">
            <mx:GridItem width="50%" height="100%">
                <mx:Label width="100%" height="100%" text="Select file and upload:" textAlign="right" />
            </mx:GridItem>
            <mx:GridItem width="50%" height="100%">
                <mx:FormItem direction="horizontal">
                    <mx:Button width="80" label="Browse" click="fileRef.browse(allTypes)" />
                    <mx:Button width="80" label="Upload" id="btn_upload" enabled="false" click="uploadFileFunction()" />
                    <mx:Button width="80" label="Cancel" id="btn_cancel" enabled="false" click="CancelFunction()" />
                </mx:FormItem>
            </mx:GridItem>
        </mx:GridRow>
        <mx:GridRow width="100%" height="30">
            <mx:GridItem width="50%" height="100%" />
            <mx:GridItem width="50%" height="100%">
                <mx:ProgressBar id="progressBar" mode="manual" />
            </mx:GridItem>
        </mx:GridRow>
        <mx:GridRow width="100%" height="30">
            <mx:GridItem width="50%" height="100%">
                <mx:Label width="100%" height="100%" text="... or download application from a URL:" textAlign="right" />
            </mx:GridItem>
            <mx:GridItem width="50%" height="100%">
                <mx:TextInput id="UrlFile" width="270" height="22" />
                <mx:Button width="90" label="Download" id="btn_download" enabled="true" click="loadUrlFile()" />
            </mx:GridItem>
        </mx:GridRow>
        <mx:GridRow width="100%" height="30">
            <mx:GridItem width="50%" height="100%">
                <mx:Label width="100%" height="100%" text="Application details:" textAlign="right" />
            </mx:GridItem>
            <mx:GridItem width="50%" height="100%">
                <mx:Label id="applicationDetails" width="100%" height="100%" />
            </mx:GridItem>
        </mx:GridRow>
        <mx:GridRow width="100%" height="20">
            <mx:GridItem width="100%" height="100%" colSpan="2" verticalAlign="middle">
                <mx:HRule width="100%" />
            </mx:GridItem>
        </mx:GridRow>
        <mx:GridRow width="100%" height="30">
            <mx:GridItem width="100%" height="100%" colSpan="2">
                <mx:Label width="100%" color="blue" text="Details on the applications currently deployed on the selected group of servers:" height="100%" fontSize="11" />
            </mx:GridItem>
        </mx:GridRow>
        <mx:GridRow width="100%" height="100%">
            <mx:GridItem width="100%" height="100%" colSpan="2">
                <view:RowColorDataGrid id="applicationlist" width="100%" textAlign="center" styleName="applicationList"
                    rowColorFunction="applicationColor" editable="false" selectable="false">
                    <view:columns>
                        <mx:DataGridColumn dataField="serverName" headerText="Server Name" />
                        <mx:DataGridColumn dataField="name" headerText="Application Name" />
                        <mx:DataGridColumn dataField="state" headerText="State" />
                        <mx:DataGridColumn dataField="version" headerText="Version" />
                        <mx:DataGridColumn dataField="policy" headerText="Policy" />
                    </view:columns>
                </view:RowColorDataGrid>
            </mx:GridItem>
        </mx:GridRow>
        <mx:GridRow width="100%" height="30">
            <mx:GridItem width="100%" height="100%" colSpan="2">
                <mx:Label width="100%" height="100%" id="deployType" textAlign="center" />
            </mx:GridItem>
        </mx:GridRow>
    </mx:Grid>
</mx:Canvas>
