Exemplo n.º 1
0
 def refresh(self):
     """Called when a session has timed out or almost timed out."""
     if self._is_cert_auth():
         return  # Certificate-based calls are session-less
     url = self._api_url('aaaRefresh')
     response = self._do_request(self.session.get, url, cookies=self.cookie)
     attributes = self._save_cookie('aaaRefresh', response)
     if response.status_code == requests.codes.ok:
         # We refreshed before the session timed out.
         self.authentication = attributes
     else:
         err_code = attributes['code']
         err_text = attributes['text']
         if (err_code == APIC_CODE_FORBIDDEN
                 and err_text.lower().startswith('token was invalid')):
             # This means the token timed out, so log in again.
             LOG.debug(("APIC session timed-out, logging in again."))
             self.login()
         else:
             self.authentication = None
             raise cexc.ApicResponseNotOk(request=url,
                                          status=response.status_code,
                                          reason=response.reason,
                                          err_text=err_text,
                                          err_code=err_code)
Exemplo n.º 2
0
 def _send(self,
           request,
           url,
           data=None,
           refreshed=None,
           accepted=None,
           sleep_offset=0):
     """Send a request and process the response."""
     curr_call = time.time()
     try:
         time.sleep((self.sleep + sleep_offset) -
                    (curr_call - self.last_call))
     except IOError:
         # Negative sleep value
         pass
     if data is None:
         response = self._do_request(request, url, cookies=self.cookie)
     else:
         response = self._do_request(request,
                                     url,
                                     data=data,
                                     cookies=self.cookie)
     self.last_call = time.time()
     if response is None:
         raise cexc.ApicHostNoResponse(url=url)
     # Every request refreshes the timeout
     self.session_deadline = time.time() + self.session_timeout
     if data is None:
         request_str = url
     else:
         request_str = '%s, data=%s' % (url, data)
         LOG.debug(("data = %s"), data)
     # imdata is where the APIC returns the useful information
     imdata = response.json().get('imdata')
     LOG.debug(("Response: %s"), imdata)
     if response.status_code != requests.codes.ok:
         try:
             err_code = imdata[0]['error']['attributes']['code']
             err_text = imdata[0]['error']['attributes']['text']
         except (IndexError, KeyError):
             err_code = '[code for APIC error not found]'
             err_text = '[text for APIC error not found]'
         # If invalid token then re-login and retry once
         if (not refreshed and (err_code in REFRESH_CODES)
                 and not self._is_cert_auth()):
             self.login()
             return self._send(request, url, data=data, refreshed=True)
         if not accepted and response.status_code == 202:
             # The APIC queue is full, slow down significantly
             return self._send(request,
                               url,
                               data=data,
                               accepted=True,
                               sleep_offset=SLEEP_ON_FULL_QUEUE)
         raise cexc.ApicResponseNotOk(request=request_str,
                                      status=response.status_code,
                                      reason=response.reason,
                                      err_text=err_text,
                                      err_code=err_code)
     return imdata
    def test_analyze_exception_not_ok(self):
        for err_code in self.base_handler.APIC_OBJECT_CRITICAL:
            self.assertEqual(
                errors.OPERATION_CRITICAL,
                self.apic_handler.analyze_exception(
                    exceptions.ApicResponseNotOk(request='',
                                                 status='400',
                                                 reason='',
                                                 err_text='',
                                                 err_code=str(err_code))))

        for err_code in self.base_handler.APIC_OBJECT_TRANSIENT:
            self.assertEqual(
                errors.OPERATION_TRANSIENT,
                self.apic_handler.analyze_exception(
                    exceptions.ApicResponseNotOk(request='',
                                                 status='400',
                                                 reason='',
                                                 err_text='',
                                                 err_code=str(err_code))))

        self.assertEqual(
            errors.SYSTEM_TRANSIENT,
            self.apic_handler.analyze_exception(
                exceptions.ApicResponseNotOk(request='',
                                             status='403',
                                             reason='',
                                             err_text='',
                                             err_code='')))

        self.assertEqual(
            errors.SYSTEM_TRANSIENT,
            self.apic_handler.analyze_exception(
                exceptions.ApicResponseNotOk(request='',
                                             status='500',
                                             reason='',
                                             err_text='',
                                             err_code='')))

        self.assertEqual(
            errors.UNKNOWN,
            self.apic_handler.analyze_exception(
                exceptions.ApicResponseNotOk(request='',
                                             status='300',
                                             reason='',
                                             err_text='',
                                             err_code='')))
Exemplo n.º 4
0
    def set_private_key(self,
                        usr,
                        cert_name,
                        private_key_file,
                        sign_algo=None,
                        sign_hash=None):
        """Set the X.509 private key used for session-less REST calls"""
        url = self._api_url('mo/%s' % self._get_cert_dn(usr, cert_name))

        try:
            with open(private_key_file) as key_file:
                private_key = crypto.load_privatekey(crypto.FILETYPE_PEM,
                                                     key_file.read())
        except Exception as e:
            LOG.error("Failed to load private key from file %s: %s" %
                      (private_key_file, e))
            raise

        self.username = usr
        self.cert_name = cert_name
        self.private_key = private_key
        self.sign_algo = sign_algo and sign_algo or 'v1.0'
        self.sign_hash = sign_hash and sign_hash or 'sha256'
        # Verify that the cert-name and key are ok
        try:
            response = self._do_request(self.session.get, url)
        except rexc.Timeout:
            raise cexc.ApicHostNoResponse(url=url)

        if response.status_code != requests.codes.ok:
            attr = response.json().get('imdata')[0]['error']['attributes']
            raise cexc.ApicResponseNotOk(request=url,
                                         status=response.status_code,
                                         reason=response.reason,
                                         err_text=attr['text'],
                                         err_code=attr['code'])
Exemplo n.º 5
0
    def login(self, usr=None, pwd=None):
        """Log in to controller. Save user name and authentication."""
        usr = usr or self.username
        pwd = pwd or self.password
        name_pwd = self._make_data('aaaUser', name=usr, pwd=pwd)
        url = self._api_url('aaaLogin')
        self.cookie = {}

        try:
            response = self._do_request(self.session.post, url, data=name_pwd)
        except rexc.Timeout:
            raise cexc.ApicHostNoResponse(url=url)
        attributes = self._save_cookie('aaaLogin', response)
        if response.status_code == requests.codes.ok:
            self.username = usr
            self.password = pwd
            self.authentication = attributes
        else:
            self.authentication = None
            raise cexc.ApicResponseNotOk(request=url,
                                         status=response.status_code,
                                         reason=response.reason,
                                         err_text=attributes['text'],
                                         err_code=attributes['code'])