← Back to team overview

duplicity-team team mailing list archive

[Merge] lp:~mstoll-de/duplicity/b2-reauth into lp:duplicity

 

Markus has proposed merging lp:~mstoll-de/duplicity/b2-reauth into lp:duplicity.

Commit message:
take care of error code 401 (which means the auth token did expired) by reauthenticating against b2 backend

Requested reviews:
  duplicity-team (duplicity-team)
Related bugs:
  Bug #1588503 in Duplicity: "b2: large uploads fail due to expired auth token"
  https://bugs.launchpad.net/duplicity/+bug/1588503

For more details, see:
https://code.launchpad.net/~mstoll-de/duplicity/b2-reauth/+merge/296496

fixes the bug #1588503 where an expired auth token did not lead to a reauthentication
-- 
Your team duplicity-team is requested to review the proposed merge of lp:~mstoll-de/duplicity/b2-reauth into lp:duplicity.
=== modified file 'duplicity/backends/b2backend.py'
--- duplicity/backends/b2backend.py	2015-12-14 22:07:20 +0000
+++ duplicity/backends/b2backend.py	2016-06-04 20:13:27 +0000
@@ -61,8 +61,16 @@
             raise BackendException("B2 requires a bucket name")
         self.path = "/".join(self.url_parts)
 
-        id_and_key = self.account_id + ":" + account_key
-        basic_auth_string = 'Basic ' + base64.b64encode(id_and_key)
+        self.id_and_key = self.account_id + ":" + account_key
+        self._authorize();
+
+        try:
+            self.find_or_create_bucket(self.bucket_name)
+        except urllib2.HTTPError:
+            raise FatalBackendException("Bucket cannot be created")
+
+    def _authorize(self):
+        basic_auth_string = 'Basic ' + base64.b64encode(self.id_and_key)
         headers = {'Authorization': basic_auth_string}
 
         request = urllib2.Request(
@@ -78,10 +86,6 @@
         self.api_url = response_data['apiUrl']
         self.download_url = response_data['downloadUrl']
 
-        try:
-            self.find_or_create_bucket(self.bucket_name)
-        except urllib2.HTTPError:
-            raise FatalBackendException("Bucket cannot be created")
 
     def _get(self, remote_filename, local_path):
         """
@@ -254,6 +258,8 @@
         If headers are not supplied, just send with an auth key
         """
         if headers is None:
+            if self.auth_token is None:
+                self._authorize();
             headers = {'Authorization': self.auth_token}
         if data_file is not None:
             data = data_file
@@ -265,12 +271,18 @@
             for (k, v) in headers.iteritems()
         )
 
-        with OpenUrl(url, data, encoded_headers) as resp:
-            out = resp.read()
+        try:
+            with OpenUrl(url, data, encoded_headers) as resp:
+                out = resp.read()
             try:
                 return json.loads(out)
             except ValueError:
                 return out
+        except urllib2.HTTPError as e:
+            if e.code == 401:
+                self.auth_token = None;
+                log.Warn("Authtoken expired, will reauthenticate with next attempt")
+            raise e
 
     def get_file_info(self, filename):
         """


References