def _get_free_vip_in_range(self, vip_range, allocated_vips):

        try:
            make_net = 0

            if "/" in vip_range:
                make_net = 1
                ip_list = IP(vip_range, make_net=make_net)

        except ValueError:
            self.logger.debug(
                "Virtual IP range %s specified in configuration file is invalid:"
                % vip_range)
            raise ServiceUnavailableException(
                "Invalid service configuration.Please contact support")

        if "-" in vip_range:
            start_address, end_address = vip_range.split('-')
        else:
            network_address = ip_list.net()
            broadcast_address = ip_list.broadcast()
            """ netmask or CIDR network notation """
            start_address = IP(network_address.int() + 1)
            end_address = IP(broadcast_address.int() - 1)

        self.logger.debug("VIP range: %s" % vip_range)
        self.logger.debug("       start address: %s" % str(start_address))
        self.logger.debug("       end address: %s" % str(end_address))

        address = self._get_free_vip_in_range2(str(start_address),
                                               str(end_address),
                                               allocated_vips)

        return address
    def _configure_pool(self, viptype, pools_config):

        if not pools_config:
            raise LoadBalancerFaultException(
                "Error in configuring Virtual IPs of type %s" % viptype)

        for vip_pool in pools_config:
            if vip_pool["name"].lower() == viptype.lower():
                pool_config = vip_pool["config"]
                break
        else:
            raise BadRequestException(
                "Validation fault", "The object is not valid",
                "VirtualIP type specified for load balancer is not a valid type"
            )

        ips_str = pool_config["ips"]
        ips = ips_str.split(",")

        ips = [ip.strip() for ip in ips]
        """ validate IP addresses and ranges found in configuration """
        for ip in ips:
            try:
                IP(ip)
            except ValueError as msg:
                self.logger.debug(
                    "Virtual IP range %s specified in configuration file is invalid:%s"
                    % (ip, msg))
                raise ServiceUnavailableException(
                    "Invalid service configuration.Please contact support")

        self.vip_pools[viptype] = ips
    def process_netscaler_task_list(self, task_list, _undoflag=True):

        if not task_list:
            return None

        if _undoflag:
            task_list = self._reorder_task_list(task_list)

        exception_error = None
        partial_failure = False
        completed_tasks = []

        for task in task_list:
            try:
                self.process_netscaler_task(task, _undoflag)
                completed_tasks.append(task)
               
            except BadRequestException as error:
                partial_failure = True
                exception_error = error
                break

            except ItemNotFoundException as error:  
                if not "ignore_notfound" in task or not task["ignore_notfound"] :      
                    partial_failure = True
                    exception_error = error
                    break

            except ImplementationErrorException as error:
                partial_failure = True
                exception_error = error
                break

            except NotImplementedException as error:
                partial_failure = True
                exception_error = error
                break


            except ItemNotFoundException as error:
                partial_failure = True
                exception_error = error
                break

            except ServiceUnavailableException as error:
                """ A problem with Netscaler. We cannot remedy this """  
                raise error


        if partial_failure:
            self.logger.debug("partial error occurred")
            try:
                self._netscaler_undo_changes(completed_tasks)  
            except Exception, e:
                raise ServiceUnavailableException("Catastrophic error. Cannot undo changes made !!")

            raise exception_error 
    def allocate_virtualIP(self, viptype, tenant_id, loadBalancerId):

        if not viptype in self.vip_pools.keys():
            self._configure_pool(viptype)

        all_vips = self.vip_pools[viptype]

        allocated_vips = self.db.get_allocated_vips(viptype)
        allocated_addresses = [vip["address"] for vip in allocated_vips]
        allocated_vipids = [vip["id"] for vip in allocated_vips]

        for vip in all_vips:
            """ Check if this is an individual entry or a range """
            if self._is_range(vip):
                self.logger.debug("already allocated vips are: %s" %
                                  str(allocated_addresses))
                free_vip = self._get_free_vip_in_range(vip,
                                                       allocated_addresses)
                if free_vip:
                    break

                continue
            else:
                if vip in allocated_addresses:
                    continue

                free_vip = vip
                break
        else:
            raise OutOfVirtualIpsException(
                "Out of virtual IPs. Please contact support so they can make available more virtual IPs for use."
            )

        vip_id = NitroUtils.generate_vipid(allocated_vipids)

        version = IP(free_vip).version()

        if version == 4:
            vip_version = "IPV4"
        elif version == 6:
            vip_version = "IPV6"
        else:
            self.logger.debug(
                "Allocated IP address %s doesn't seem to be IPV4 or IPV6 !!" %
                free_vip)
            raise ServiceUnavailableException(
                "Internal error.Please contact support")

        self.db.allocate_vip(vip_id, free_vip, viptype, vip_version, tenant_id,
                             loadBalancerId)

        self.logger.debug(
            "Allocated VIP: address=%s ipVersion=%s  type=%s id=%s" %
            (free_vip, vip_version, viptype, vip_id))

        return free_vip
    def nitro_login(self):

        headers = {'Content-Type':'application/x-www-form-urlencoded'} 

        body='object={ "login":{"username":"******","password":"******"}}' % (self.conn.user,self.conn.password)
        
        url = self.conn.path

        status, response = self._nitro_perform_http_request('POST', url, headers, body)


        if status != "SUCCESS":
	    raise ServiceUnavailableException("The Load Balancing Service is currently unavailable. Please contact support")

        if response["sessionid"]:
            self.conn.sessionid = response["sessionid"]
        else:
            self.logger.debug("Error: Login failed! status code returned by Netscaler =%d" % repr(resp_dict['errorcode']))
	    raise ServiceUnavailableException("The Load Balancing Service is currently unavailable. Please contact support")        
Example #6
0
    def auth(self, account, token):
        """
        Dev authorization implmentation

        :param account: account name
        :param token: auth token

        :returns: True if authorization is successful, False otherwise
        """
        return True
        key = 'auth/%s/%s' % (account, token)
        now = time.time()

        if self.memcache_client:
            cached_auth_data = self.memcache_client.get(key)
        else:
            cached_auth_data = None

        if cached_auth_data:
            start, expiration = cached_auth_data
            if now - start <= expiration:
                return True
        try:
            with Timeout(self.timeout):
                """
                conn = http_connect(self.auth_host, self.auth_port, 'GET',
                    '/token/%s/%s' % (account, token), ssl=True)
                """
                conn = http_connect(self.auth_host, self.auth_port, 'GET',
                    '/token/%s' % token, ssl=True)
                resp = conn.getresponse()
                resp.read()
                conn.close()
                if resp.status == 204:
                    validated = float(resp.getheader('x-auth-ttl'))
                else:
                    validated = False
                
        except:
            self.logger.exception('auth_host: %s' % self.auth_host)
            self.logger.exception('auth_port: %s' % self.auth_port)
            self.logger.exception('ERROR with auth')
            raise ServiceUnavailableException("The Auth Service is currently unavailable. Please try later")


        if not validated:
            return False
        else:
            val = (now, validated)

            if self.memcache_client:
                self.memcache_client.set(key, val, timeout=validated)

            return True
    def SetUp(logger, conf):

        plugin_config = conf["plugin"]

        connmanager = NitroConnectionManager(plugin_config, logger)
        
        logger.debug("Connection Manager is: %s" % repr(connmanager))

        if not connmanager:
            logger.debug("Error: Setting up adaptor failed")
	    raise ServiceUnavailableException("The Load Balancing Service is currently unavailable. Please contact support")

        """"No Error occurred"""
        return CitrixNetScalerLBService(connmanager, conf, logger)
Example #8
0
    def make_service_call(self, req, env, method_dict, variables):

        try:
            req_method = req.method.upper()

            call_pattern = method_dict[req_method]

            call_pattern = self.replace_variables(req, call_pattern, variables)

            self.logger.debug("Call on resource is: %s" % str(call_pattern))

            response = eval(call_pattern)

        except BadRequestException as error:

            content_type, detail = self.get_error_body(req, error)

            return HTTPBadRequest(body=detail,
                                  content_type=content_type,
                                  request=req)

        except NotImplementedException as error:

            content_type, detail = self.get_error_body(req, error)

            return HTTPNotImplemented(body=detail,
                                      content_type=content_type,
                                      request=req)

        except ServiceUnavailableException as error:

            content_type, detail = self.get_error_body(req, error)

            return HTTPInternalServerError(body=detail,
                                           content_type=content_type,
                                           request=req)

        except ItemNotFoundException as error:

            content_type, detail = self.get_error_body(req, error)

            return HTTPNotFound(body=detail,
                                content_type=content_type,
                                request=req)

        except OverLimitException as error:

            content_type, detail = self.get_error_body(req, error)

            return HTTPRequestEntityTooLarge(body=detail,
                                             content_type=content_type,
                                             request=req)

        except ImmutableEntityException as error:

            content_type, detail = self.get_error_body(req, error)

            return HTTPUnprocessableEntity(body=detail,
                                           content_type=content_type,
                                           request=req)

        except LoadBalancerFaultException as error:

            content_type, detail = self.get_error_body(req, error)

            return HTTPUnauthorized(body=detail,
                                    content_type=content_type,
                                    request=req)

        except Exception, msg:

            exc_type, exc_value, exc_tb = sys.exc_info()

            tb = traceback.format_exception(exc_type, exc_value, exc_tb)

            tb.reverse()

            tb_str = ''.join(tb)

            self.logger.debug("cannot eval(%s) because %s. Traceback: %s" %
                              (call_pattern, msg, tb_str))

            error = ServiceUnavailableException(
                "The Load Balancing Service is currently unavailable." +
                " Please contact support")

            content_type, detail = self.get_error_body(req, error)

            return HTTPInternalServerError(body=detail,
                                           content_type=content_type,
                                           request=req)