Skip to content

Instantly share code, notes, and snippets.

@bloodeagle40234
Last active December 6, 2016 02:39
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save bloodeagle40234/2d747f44909d3d3f153a27a70afb7a39 to your computer and use it in GitHub Desktop.
Save bloodeagle40234/2d747f44909d3d3f153a27a70afb7a39 to your computer and use it in GitHub Desktop.
diff --git a/swift/obj/updater.py b/swift/obj/updater.py
index bcb73dd..9510216 100644
--- a/swift/obj/updater.py
+++ b/swift/obj/updater.py
@@ -31,7 +31,8 @@ from swift.common.utils import get_logger, renamer, write_pickle, \
from swift.common.daemon import Daemon
from swift.common.storage_policy import split_policy_string, PolicyError
from swift.obj.diskfile import get_tmp_dir, ASYNCDIR_BASE
-from swift.common.http import is_success, HTTP_INTERNAL_SERVER_ERROR
+from swift.common.http import is_success, HTTP_INTERNAL_SERVER_ERROR, \
+ HTTP_NOT_FOUND
class ObjectUpdater(Daemon):
@@ -225,16 +226,18 @@ class ObjectUpdater(Daemon):
events = [spawn(self.object_update,
node, part, update['op'], obj, headers_out)
for node in nodes if node['id'] not in successes]
- success = True
new_successes = False
+ failures = []
for event in events:
- event_success, node_id = event.wait()
- if event_success is True:
+ status, node_id = event.wait()
+ if is_success(status) is True:
successes.append(node_id)
new_successes = True
else:
- success = False
- if success:
+ failures.append((status, node_id))
+
+ # no failures
+ if not failures:
self.successes += 1
self.logger.increment('successes')
self.logger.debug('Update sent for %(obj)s %(path)s',
@@ -246,6 +249,22 @@ class ObjectUpdater(Daemon):
self.logger.increment('failures')
self.logger.debug('Update failed for %(obj)s %(path)s',
{'obj': obj, 'path': update_path})
+
+ # This is a special case, ede42c77f1e04ab571c21b1d6342e662c7eced53
+ # wants to resolve. For the case, updater got 404s from all
+ # primaries and it doesn't give up the object update expecting
+ # they are in handoffs but it may not be in good health so dump
+ # warning line only for this state
+ failure_status_list = [
+ status for status, node_id in failures]
+ if len(set(failure_status_list)) == 1 and \
+ failure_status_list[0] == HTTP_NOT_FOUND:
+ self.logger.warning(
+ 'Update failed because all primaries return 404'
+ '%(obj)s %(path)s %(nodes)s',
+ {'obj': obj, 'path': update_path,
+ 'nodes': [_node_id for status_int, _node_id in failures]})
+
if new_successes:
update['successes'] = successes
write_pickle(update, update_path, os.path.join(
@@ -260,6 +279,8 @@ class ObjectUpdater(Daemon):
:param op: operation performed (ex: 'PUT' or 'DELETE')
:param obj: object name being updated
:param headers_out: headers to send with the update
+
+ :returns: a tuple (status code int, node id) for the update request
"""
try:
with ConnectionTimeout(self.conn_timeout):
@@ -268,14 +289,7 @@ class ObjectUpdater(Daemon):
with Timeout(self.node_timeout):
resp = conn.getresponse()
resp.read()
- success = is_success(resp.status)
- if not success:
- self.logger.debug(
- _('Error code %(status)d is returned from remote '
- 'server %(ip)s: %(port)s / %(device)s'),
- {'status': resp.status, 'ip': node['ip'],
- 'port': node['port'], 'device': node['device']})
- return (success, node['id'])
+ return (resp.status, node['id'])
except (Exception, Timeout):
self.logger.exception(_('ERROR with remote server '
'%(ip)s:%(port)s/%(device)s'), node)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment