// Licensed to the Apache Software Foundation (ASF) under one
// or more contributor license agreements.  See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership.  The ASF licenses this file
// to you under the Apache License, Version 2.0 (the
// "License"); you may not use this file except in compliance
// with the License.  You may obtain a copy of the License at
//
//   http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing,
// software distributed under the License is distributed on an
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
// KIND, either express or implied.  See the License for the
// specific language governing permissions and limitations
// under the License. 
(function($, cloudStack) {
  var elems = {
    aclDialog: function(args) {
      var isDialog = args.isDialog;
      var actionArgs = args.actionArgs;
      var context = args.context;
      var $acl = $('<div>').addClass('acl').multiEdit(
        $.extend(true, {}, actionArgs.multiEdit, {
          context: context
        })
      );

      // Show ACL dialog
      if (isDialog) {
        $acl.dialog({
          title: _l('label.configure.network.ACLs'),
          dialogClass: 'configure-acl',
          width: 900,
          height: 600,
          buttons: {
            'Done': function() {
              $(':ui-dialog').remove();
              $('.overlay').remove();
            }
          }
        });
      }

      return $acl;
    },
    vpcConfigureTooltip: function(args) {
      var context = args.context;
      var $browser = args.$browser;
      var $chart = args.$chart;
      var ipAddresses = args.ipAddresses;
      var acl = args.acl;
      var gateways = args.gateways;
      var siteToSiteVPN = args.siteToSiteVPN;
      var links = {
        'ip-addresses': _l('label.menu.ipaddresses'),
        'gateways': _l('label.private.Gateway'),
        'site-to-site-vpn': _l('label.site.to.site.VPN'),
        'network-acls':  _l('label.network.ACLs')
      };
      var $links = $('<ul>').addClass('links');
      var $tooltip = $('<div>').addClass('vpc-configure-tooltip').append(
        $('<div>').addClass('arrow')
      );
      var tierDetailView = args.tierDetailView;

      // Make links
      $.map(links, function(label, id) {
        var $link = $('<li>').addClass('link').addClass(id);
        var $label = $('<span>').html(label);

        $link.append($label);
        $link.appendTo($links);

        // Link event
        $link.click(function() {
          switch (id) {
          case 'network-acls':
              $browser.cloudBrowser('addPanel', {
              title: _l('label.network.ACLs'),
              maximizeIfSelected: true,
              complete: function($panel) {
                $panel.listView(
                  $.extend(true, {}, acl.listView, {
                    listView: {
                      actions: {
                        add: {
                          label: 'label.add.network.ACL',
                          action: {
                            custom: function() {
                              elems.aclDialog({
                                isDialog: true,
                                actionArgs: acl,
                                context: context
                              });
                            }
                          }
                        }
                      },
                      detailView: function() {
                        var detailView = $.extend(true, {}, tierDetailView);

                        detailView.tabs = {
                          acl: tierDetailView.tabs.acl
                        };

                        return detailView;
                      }
                    }
                  }),
                  { context: acl.context }
                );
              }
            });
            break;

          case 'ip-addresses':
            $browser.cloudBrowser('addPanel', {
              title: _l('label.menu.ipaddresses'),
              maximizeIfSelected: true,
              complete: function($panel) {
                //ipAddresses.listView is a function
                $panel.listView(ipAddresses.listView(), {context: ipAddresses.context});
              }
            });
            break;
          case 'gateways':
            //siteToSiteVPN is an object
            var addAction = gateways.add;
            var isGatewayPresent = addAction.preCheck({ context: gateways.context });
            var showGatewayListView = function() {
              $browser.cloudBrowser('addPanel', {
                title: _l('label.private.Gateway'),
                maximizeIfSelected: true,
                complete: function($panel) {
                  $panel.listView(gateways.listView(), { context: gateways.context });
                }
              });
            };

            if (isGatewayPresent) {
              showGatewayListView();
            } else {
              cloudStack.dialog.createForm({
                form: addAction.createForm,
								context: args.gateways.context,
                after: function(args) {
                  var data = args.data;
                  var error = function(message) {
                    cloudStack.dialog.notice({ message: message });
                  };

                  addAction.action({
                    data: data,
                    context: gateways.context,
                    response: {
                      success: function(args) {
                        var _custom = args._custom;
                        var notification = {
                          poll: addAction.notification.poll,
                          _custom: _custom,
                          desc: addAction.messages.notification()
                        };
                        var success = function(args) {
                          if (!$chart.is(':visible')) return;

                          cloudStack.dialog.confirm({
                            message: 'Gateway for VPC has been created successfully. Would you like to see its details?',
                            action: showGatewayListView
                          });
                        };

                        cloudStack.dialog.notice({
                          message: 'Your gateway is being created; please see notifications window.'
                        });
                        
                        cloudStack.ui.notifications.add(
                          notification,
                          success, {},
                          error, {}
                        );
                      },
                      error: error
                    }
                  });
                }
              });
            }
            break;
          case 'site-to-site-vpn':
            //siteToSiteVPN is an object
            var addAction = siteToSiteVPN.add;
            var isVPNPresent = addAction.preCheck({ context: siteToSiteVPN.context });
            var showVPNListView = function() {
              $browser.cloudBrowser('addPanel', {
                title: _l('label.site.to.site.VPN'),
                maximizeIfSelected: true,
                complete: function($panel) {
                  $panel.listView(siteToSiteVPN, {context: siteToSiteVPN.context});
                }
              });
            };

            if (isVPNPresent) {
              showVPNListView();
            } else {
              cloudStack.dialog.confirm({
                message: 'Please confirm that you want to add a Site-to-Site VPN gateway.',
                action: function() {
                  var error = function(message) {
                    cloudStack.dialog.notice({ message: message });
                  };

                  addAction.action({
                    context: siteToSiteVPN.context,
                    response: {
                      success: function(args) {
                        var _custom = args._custom;
                        var notification = {
                          poll: addAction.notification.poll,
                          _custom: _custom,
                          desc: addAction.messages.notification()
                        };
                        var success = function(args) {
                          if (!$chart.is(':visible')) return;
                          cloudStack.dialog.confirm({
                            message: 'Gateway for VPC has been created successfully. Would you like to see its details?',
                            action: showVPNListView
                          });
                        };
                        
                        cloudStack.dialog.notice({
                          message: 'Your VPN is being created; please see notifications window.'
                        });
                        
                        cloudStack.ui.notifications.add(
                          notification,
                          success, {},
                          error, {}
                        );
                      },
                      error: error
                    }
                  });
                }
              });
            }
            break;
          }
        });
      });

      $tooltip.append($links);

      // Tooltip hover event
      $tooltip.hover(
        function() {
          $tooltip.addClass('active');
        },
        function() {
          $tooltip.removeClass('active');

          setTimeout(function() {
            if (!$tooltip.hasClass('active')) {
              $tooltip.remove();
            }
          }, 500);
        }
      );

      return $tooltip;
    },
    vpcConfigureArea: function(args) {
      var context = args.context;
      var $browser = args.$browser;
      var $chart = args.$chart;
      var ipAddresses = args.ipAddresses;
      var acl = args.acl;
      var gateways = args.gateways;
      var siteToSiteVPN = args.siteToSiteVPN;
      var $config = $('<div>').addClass('config-area');
      var $configIcon = $('<span>').addClass('icon').html('&nbsp');
      var tierDetailView = args.tierDetailView;
      
      $config.append($configIcon);

      // Tooltip event
      $configIcon.mouseover(function() {
        var $tooltip = elems.vpcConfigureTooltip({
          context: context,
          $browser: $browser,
          $chart: $chart,
          ipAddresses: ipAddresses,
          gateways: gateways,
          acl: acl,
          siteToSiteVPN: siteToSiteVPN,
          tierDetailView: tierDetailView
        });

        // Make sure tooltip is center aligned with icon
        $tooltip.css({ left: $configIcon.position().left });
        $tooltip.appendTo($config).hide();
        $tooltip.stop().fadeIn('fast');
      });

      return $config;
    },
    router: function(args) {
      var $browser = args.$browser;
      var detailView = args.detailView;
      var $router = $('<li>').addClass('tier virtual-router');
      var $title = $('<span>').addClass('title').html(_l('label.virtual.router'));

      $router.append($title);

      // Append horizontal chart line
      $router.append($('<div>').addClass('connect-line'));

      $router.click(function() {
        if ($router.hasClass('disabled')) return false;

        $browser.cloudBrowser('addPanel', {
          title: _l('label.VPC.router.details'),
          complete: function($panel) {
            $panel.detailView(detailView);
          }
        });
      });

      return $router;
    },
    tier: function(args) {
      var ipAddresses = args.ipAddresses;
      var acl = args.acl;
      var name = args.name;
      var cidr = args.cidr;
      var context = args.context;
      var vmListView = args.vmListView;
      var actionPreFilter = args.actionPreFilter;
      var actions = $.map(
        args.actions ? args.actions : {}, function(value, key) {
          return {
            id: key,
            action: value
          };
        }
      );
      var detailView = args.detailView;
      var $browser = args.$browser;
      var isPlaceholder = args.isPlaceholder;
      var virtualMachines = args.virtualMachines;
      var $tier = $('<li>').addClass('tier');
      var $title = $('<span>').addClass('title');
      var $cidr = $('<span>').addClass('cidr');
      var $vmCount = $('<span>').addClass('vm-count');
      var $actions = $('<div>').addClass('actions');

      // Ignore special actions
      // -- Add tier action is handled separately
      actions = $.grep(actions, function(action) {
        return action.id != 'add';
      });

      // Add loading indicator
      $vmCount.append(
        $('<div>').addClass('loading-overlay')
          .attr('title', 'VMs are launching in this tier.')
      );

      // VM count shows instance list
      $vmCount.click(function() {
        var $dialog = $('<div>');
        var $listView = $('<div>').listView($.extend(true, {}, vmListView, {
          context: context
        }));

        $dialog.append($listView);
        $dialog.dialog({
          title: _l('label.VMs.in.tier') + ': ' + name,
          dialogClass: 'multi-edit-add-list panel configure-acl',
          width: 825,
          height: 600,
          buttons: {
            'Done': function() {
              $(':ui-dialog').remove();
              $('.overlay').remove();
            }
          }
        }).closest('.ui-dialog').overlay();
      });

      // Title shows tier details
      $title.click(function() {
        if ($browser && $browser.size()) { // Fix null exception, if add tier returns error
          $browser.cloudBrowser('addPanel', {
            title: name,
            maximizeIfSelected: true,
            complete: function($panel) {
              $panel.detailView($.extend(true, {}, detailView, {
                $browser: $browser,
                context: context
              }));
            }
          });
        }
      });

      if (isPlaceholder) {
        $tier.addClass('placeholder');
        $title.html(_l('label.add.new.tier'));
      } else {        
        $title.html(
          cloudStack.concat(name, 8)
        );
        $title.attr('title', name);
        $cidr.html(cidr);
        $vmCount.append(
          $('<span>').addClass('total').html(virtualMachines != null? virtualMachines.length: 0),
          _l('label.vms')
        );
        $tier.append($actions);

        // Build action buttons
        $(actions).map(function(index, action) {
          var $action = $('<div>').addClass('action');
          var shortLabel = action.action.shortLabel;
          var label = action.action.label;

          $action.addClass(action.id);

          if (action.id != 'remove') {
            $action.append($('<span>').addClass('label').html(_l(shortLabel)));
          } else {
            $action.append($('<span>').addClass('icon').html('&nbsp;'));
          }

          $actions.append($action);
          $action.attr('title', label);
          $action.data('vpc-tier-action-id', action.id);

          // Action event
          $action.click(function() {
            if ($action.hasClass('disabled')) {
              return false;
            }

            tierAction({
              action: action,
              actionPreFilter: actionPreFilter,
              context: context,
              $tier: $tier,
              $actions: $actions
            });

            return true;
          });
        });
      }

      $tier.prepend($title);

      if (!isPlaceholder) {
        $tier.append($title, $cidr, $vmCount);
      }

      // Append horizontal chart line
      $tier.append($('<div>').addClass('connect-line'));

      // Handle action filter
      filterActions({
        $actions: $actions,
        actionPreFilter: actionPreFilter,
        context: context
      });

      return $tier;
    },
    chart: function(args) {
      var $browser = args.$browser;
      var acl = args.acl;
      var ipAddresses = args.ipAddresses;
      var gateways = args.gateways;
      var siteToSiteVPN = args.siteToSiteVPN;
      var tiers = args.tiers;
      var vmListView = args.vmListView;
      var actions = args.actions;
      var actionPreFilter = args.actionPreFilter;
      var vpcName = args.vpcName;
      var context = args.context;
      var tierDetailView = args.tierDetailView;
      var $tiers = $('<ul>').addClass('tiers');
      var $router;

      $router = elems.router({
        $browser:$browser,
        detailView:$.extend(true, {}, args.routerDetailView(), {
          context:context
        })
      });

      if (!isAdmin()) $router.addClass('disabled');

      var $chart = $('<div>').addClass('vpc-chart');
      var $title = $('<div>').addClass('vpc-title')
        .append(
        $('<span>').html(vpcName)
      )
        .append(
        elems.vpcConfigureArea({
          context:context,
          $browser:$browser,
          $chart:$chart,
          ipAddresses:$.extend(ipAddresses, {context:context}),
          gateways:$.extend(gateways, {context:context}),
          siteToSiteVPN:$.extend(siteToSiteVPN, {context:context}),
          acl:$.extend(acl, {context:context}),
          tierDetailView:tierDetailView
        })
      );

      var showAddTierDialog = function () {
        if ($(this).find('.loading-overlay').size()) {
          return false;
        }

        addTierDialog({
          ipAddresses:ipAddresses,
          $browser:$browser,
          tierDetailView:tierDetailView,
          $tiers:$tiers,
          acl:acl,
          context:context,
          actions:actions,
          vmListView:vmListView,
          actionPreFilter:actionPreFilter
        });

        return true;
      };

      if (tiers != null && tiers.length > 0) {
        $(tiers).map(function (index, tier) {
          var $tier = elems.tier({
            ipAddresses:ipAddresses,
            acl:acl,
            $browser:$browser,
            detailView:tierDetailView,
            name:tier.name,
            cidr:tier.cidr,
            virtualMachines:tier.virtualMachines,
            vmListView:vmListView,
            actions:actions,
            actionPreFilter:actionPreFilter,
            context:$.extend(true, {}, context, {
              networks:[tier]
            })
          });

          $tier.appendTo($tiers);
        });

      }

      elems.tier({ isPlaceholder:true }).appendTo($tiers)
        .click(showAddTierDialog);
      $tiers.prepend($router);
      $chart.append($title, $tiers);

      if (!tiers || !tiers.length) {
        showAddTierDialog();
      }

      return $chart;
    }
  };

  var filterActions = function(args) {
    var $actions = args.$actions;
    var actionPreFilter = args.actionPreFilter;
    var context = args.context;
    var disabledActions, allowedActions;

    disabledActions = actionPreFilter ? actionPreFilter({
      context: context
    }) : [];

    // Visual appearance for disabled actions
    $actions.find('.action').map(function(index, action) {
      var $action = $(action);
      var actionID = $action.data('vpc-tier-action-id');

      if ($.inArray(actionID, disabledActions) > -1) {
        $action.addClass('disabled');
      } else {
        $action.removeClass('disabled');
      }
    });
  };

  // Handles tier action, including UI effects
  var tierAction = function(args) {
    var $tier = args.$tier;
    var $loading = $('<div>').addClass('loading-overlay');
    var $actions = args.$actions;
    var actionArgs = args.action.action;
    var action = actionArgs.action;
    var actionID = args.action.id;
    var notification = actionArgs.notification;
    var label = actionArgs.label;
    var context = args.context;
    var actionPreFilter = args.actionPreFilter;

    var success = function(args) {
      var remove = args ? args.remove : false;
      var _custom = args ? args._custom : {};

      var updateVMLoadingState = function() {
        var pendingVMs = $tier.data('vpc-tier-pending-vms');

        pendingVMs = pendingVMs ? pendingVMs - 1 : 0;

        if (!pendingVMs) {
          $tier.data('vpc-tier-pending-vms', 0);
          $tier.removeClass('loading');
        } else {
          $tier.data('vpc-tier-pending-vms', pendingVMs);
        }
      };

      cloudStack.ui.notifications.add(
        // Notification
        {
          desc: label,
          poll: notification.poll,
          _custom: _custom
        },

        // Success
        function(args) {
          if (actionID == 'addVM') {
            // Increment VM total
            var $total = $tier.find('.vm-count .total');
            var prevTotal = parseInt($total.html());
            var newTotal = prevTotal + 1;
            var newVM = args.data;
            var newContext = $.extend(true, {}, context, {
              vms: [newVM]
            });

            $total.html(newTotal);

            filterActions({
              $actions: $actions,
              actionPreFilter: actionPreFilter,
              context: newContext
            });

            updateVMLoadingState();
          } else if (actionID == 'remove') { //remove tier
            $loading.remove();
            $tier.remove();
          } else {
            $loading.remove();
          }

        },

        {},

        // Error
        function(args) {
          if (actionID == 'addVM') {
            updateVMLoadingState();
          } else {
            $loading.remove();
          }
        }
      );
    };

    switch(actionID) {
    case 'addVM':
      action({
        context: context,
        complete: function(args) {
          var pendingVMs = $tier.data('vpc-tier-pending-vms');

          pendingVMs = pendingVMs ? pendingVMs + 1 : 1;
          $tier.addClass('loading');
          $tier.data('vpc-tier-pending-vms', pendingVMs);
          success(args);
        }
      });
      break;
    case 'remove':
      $loading.appendTo($tier);
      action({
        context: context,
        response: {
          success: function(args) {
            success($.extend(args, {
              remove: true
            }));
          }
        }
      });
      break;
    case 'acl':
      elems.aclDialog({
        isDialog: true,
        actionArgs: actionArgs,
        context: context  
      }).closest('.ui-dialog').overlay();
      break;
    default:
      $loading.appendTo($tier);
      action({
        context: context,
        complete: success,
        response: {
          success: success,
          error: function(args) { $loading.remove(); }
        }
      });
    }
  };

  // Appends a new tier to chart
  var addNewTier = function(args) {
    var ipAddresses = args.ipAddresses;
    var acl = args.acl;
    var actions = args.actions;
    var vmListView = args.vmListView;
    var actionPreFilter = args.actionPreFilter;
    var context = args.context;
    var $browser = args.$browser;
    var tierDetailView = args.tierDetailView;
    var tier = $.extend(args.tier, {
      ipAddresses: ipAddresses,
      $browser: $browser,
      detailView: tierDetailView,
      context: context,
      vmListView: vmListView,
      actions: actions,
      actionPreFilter: actionPreFilter,
      acl: acl,
      virtualMachines: []
    });
    var $tiers = args.$tiers;

    $tiers.find('li.placeholder')
      .before(
        elems.tier(tier)
          .hide()
          .fadeIn('slow')
      );
  };

  // Renders the add tier form, in a dialog
  var addTierDialog = function(args) {
    var ipAddresses = args.ipAddresses;
    var actions = args.actions;
    var context = args.context;
    var vmListView = args.vmListView;
    var actionPreFilter = args.actionPreFilter;
    var $tiers = args.$tiers;
    var $browser = args.$browser;
    var tierDetailView = args.tierDetailView;
    var acl = args.acl;

    cloudStack.dialog.createForm({
      context: context,
      form: actions.add.createForm,
      after: function(args) {
        var $loading = $('<div>').addClass('loading-overlay').prependTo($tiers.find('li.placeholder'));
        actions.add.action({
          context: context,
          data: args.data,
          response: {
            success: function(args) {
              var tier = args.data;

              cloudStack.ui.notifications.add(
                // Notification
                {
                  desc: actions.add.label
                },

                // Success
                function(args) {
                  $loading.remove();
                  addNewTier({
                    ipAddresses: ipAddresses,
                    $browser: $browser,
                    tierDetailView: tierDetailView,
                    context: $.extend(true, {}, context, {
                      networks: [tier]
                    }),
                    tier: tier,
                    acl: acl,
                    $tiers: $tiers,
                    actions: actions,
                    actionPreFilter: actionPreFilter,
                    vmListView: vmListView
                  });
                },

                {},

                // Error
                function(args) {
                  $loading.remove();
                }
              );
            },
            error: function(errorMsg) {
              cloudStack.dialog.notice({ message: _s(errorMsg) });
              $loading.remove();
            }
          }
        });
      }
    });
  };

  cloudStack.uiCustom.vpc = function(args) {
    var vmListView = args.vmListView;
    var tierArgs = args.tiers;
    var ipAddresses = args.ipAddresses;
    var gateways = args.gateways;
    var acl = args.acl;
    var siteToSiteVPN = args.siteToSiteVPN;
    var routerDetailView = args.routerDetailView;

    return function(args) {
      var context = args.context;
      var $browser = $('#browser .container');
      var $toolbar = $('<div>').addClass('toolbar');
      var vpc = args.context.vpc[0];

      $browser.cloudBrowser('addPanel', {
        maximizeIfSelected: true,
        title: _l('label.configure.vpc') + ': ' + vpc.name,
        complete: function($panel) {
          var $loading = $('<div>').addClass('loading-overlay').appendTo($panel);

          $panel.append($toolbar);

          // Load data
          tierArgs.dataProvider({
            context: context,
            response: {
              success: function(args) {
                // Setup detail view tabs
                var tierDetailView = $.extend(true, {}, tierArgs.detailView, {
                  tabs: {
                    acl: {
                      custom: function(args) {
                        var $acl = elems.aclDialog({
                          isDialog: false,
                          actionArgs: acl,
                          context: args.context
                        });
                        
                        return $acl;
                      }
                    },
                    ipAddresses: {
                      custom: function(args) {
                        return $('<div>').listView(ipAddresses.listView(),
                                                   {context: args.context});
                      }
                    }
                  }
                });
                
                var tiers = args.tiers;
                var $chart = elems.chart({
                  $browser: $browser,
                  ipAddresses: ipAddresses,
                  gateways: gateways,
                  acl: acl,
                  tierDetailView: tierDetailView,
                  routerDetailView: routerDetailView,
                  siteToSiteVPN: siteToSiteVPN,
                  vmListView: vmListView,
                  context: context,
                  actions: tierArgs.actions,
                  actionPreFilter: tierArgs.actionPreFilter,
                  vpcName: vpc.name,
                  tiers: tiers
                }).appendTo($panel);

                $loading.remove();
                $chart.fadeIn(function() {
                });
              }
            }
          });
        }
      });
    };
  };
}(jQuery, cloudStack));
