Remove redundant syscalls

This will optimize the first GET on files added from file interface.
More info: https://gist.github.com/prashanthpai/62e0bec770421561ea79

Change-Id: I3f0fd897eedf1413c3e7d5dca0f6196c62549fcb
Signed-off-by: Prashanth Pai <ppai@redhat.com>
This commit is contained in:
Prashanth Pai 2015-11-17 18:11:31 +05:30
parent 8bce87a2bb
commit 60eaebbb01
3 changed files with 19 additions and 24 deletions

View File

@ -292,18 +292,19 @@ def _get_etag(path_or_fd):
return etag return etag
def get_object_metadata(obj_path_or_fd): def get_object_metadata(obj_path_or_fd, stats=None):
""" """
Return metadata of object. Return metadata of object.
""" """
if isinstance(obj_path_or_fd, int): if not stats:
# We are given a file descriptor, so this is an invocation from the if isinstance(obj_path_or_fd, int):
# DiskFile.open() method. # We are given a file descriptor, so this is an invocation from the
stats = do_fstat(obj_path_or_fd) # DiskFile.open() method.
else: stats = do_fstat(obj_path_or_fd)
# We are given a path to the object when the DiskDir.list_objects_iter else:
# method invokes us. # We are given a path to the object when the
stats = do_stat(obj_path_or_fd) # DiskDir.list_objects_iter method invokes us.
stats = do_stat(obj_path_or_fd)
if not stats: if not stats:
metadata = {} metadata = {}
@ -320,8 +321,7 @@ def get_object_metadata(obj_path_or_fd):
return metadata return metadata
def restore_metadata(path, metadata): def restore_metadata(path, metadata, meta_orig):
meta_orig = read_metadata(path)
if meta_orig: if meta_orig:
meta_new = meta_orig.copy() meta_new = meta_orig.copy()
meta_new.update(metadata) meta_new.update(metadata)
@ -332,12 +332,12 @@ def restore_metadata(path, metadata):
return meta_new return meta_new
def create_object_metadata(obj_path_or_fd): def create_object_metadata(obj_path_or_fd, stats=None, existing_meta={}):
# We must accept either a path or a file descriptor as an argument to this # We must accept either a path or a file descriptor as an argument to this
# method, as the diskfile modules uses a file descriptior and the DiskDir # method, as the diskfile modules uses a file descriptior and the DiskDir
# module (for container operations) uses a path. # module (for container operations) uses a path.
metadata = get_object_metadata(obj_path_or_fd) metadata_from_stat = get_object_metadata(obj_path_or_fd, stats)
return restore_metadata(obj_path_or_fd, metadata) return restore_metadata(obj_path_or_fd, metadata_from_stat, existing_meta)
# The following dir_xxx calls should definitely be replaced # The following dir_xxx calls should definitely be replaced

View File

@ -636,8 +636,8 @@ class DiskFile(object):
self._metadata = read_metadata(self._fd) self._metadata = read_metadata(self._fd)
if not validate_object(self._metadata, self._stat): if not validate_object(self._metadata, self._stat):
create_object_metadata(self._fd) self._metadata = create_object_metadata(self._fd, self._stat,
self._metadata = read_metadata(self._fd) self._metadata)
assert self._metadata is not None assert self._metadata is not None
self._filter_metadata() self._filter_metadata()

View File

@ -320,10 +320,9 @@ class TestUtils(unittest.TestCase):
def test_restore_metadata_none(self): def test_restore_metadata_none(self):
# No initial metadata # No initial metadata
path = "/tmp/foo/i" path = "/tmp/foo/i"
res_d = utils.restore_metadata(path, {'b': 'y'}) res_d = utils.restore_metadata(path, {'b': 'y'}, {})
expected_d = {'b': 'y'} expected_d = {'b': 'y'}
assert res_d == expected_d, "Expected %r, result %r" % (expected_d, res_d) assert res_d == expected_d, "Expected %r, result %r" % (expected_d, res_d)
assert _xattr_op_cnt['get'] == 1, "%r" % _xattr_op_cnt
assert _xattr_op_cnt['set'] == 1, "%r" % _xattr_op_cnt assert _xattr_op_cnt['set'] == 1, "%r" % _xattr_op_cnt
def test_restore_metadata(self): def test_restore_metadata(self):
@ -332,10 +331,9 @@ class TestUtils(unittest.TestCase):
initial_d = {'a': 'z'} initial_d = {'a': 'z'}
xkey = _xkey(path, utils.METADATA_KEY) xkey = _xkey(path, utils.METADATA_KEY)
_xattrs[xkey] = serialize_metadata(initial_d) _xattrs[xkey] = serialize_metadata(initial_d)
res_d = utils.restore_metadata(path, {'b': 'y'}) res_d = utils.restore_metadata(path, {'b': 'y'}, initial_d)
expected_d = {'a': 'z', 'b': 'y'} expected_d = {'a': 'z', 'b': 'y'}
assert res_d == expected_d, "Expected %r, result %r" % (expected_d, res_d) assert res_d == expected_d, "Expected %r, result %r" % (expected_d, res_d)
assert _xattr_op_cnt['get'] == 1, "%r" % _xattr_op_cnt
assert _xattr_op_cnt['set'] == 1, "%r" % _xattr_op_cnt assert _xattr_op_cnt['set'] == 1, "%r" % _xattr_op_cnt
def test_restore_metadata_nochange(self): def test_restore_metadata_nochange(self):
@ -344,10 +342,9 @@ class TestUtils(unittest.TestCase):
initial_d = {'a': 'z'} initial_d = {'a': 'z'}
xkey = _xkey(path, utils.METADATA_KEY) xkey = _xkey(path, utils.METADATA_KEY)
_xattrs[xkey] = serialize_metadata(initial_d) _xattrs[xkey] = serialize_metadata(initial_d)
res_d = utils.restore_metadata(path, {}) res_d = utils.restore_metadata(path, {}, initial_d)
expected_d = {'a': 'z'} expected_d = {'a': 'z'}
assert res_d == expected_d, "Expected %r, result %r" % (expected_d, res_d) assert res_d == expected_d, "Expected %r, result %r" % (expected_d, res_d)
assert _xattr_op_cnt['get'] == 1, "%r" % _xattr_op_cnt
assert _xattr_op_cnt['set'] == 0, "%r" % _xattr_op_cnt assert _xattr_op_cnt['set'] == 0, "%r" % _xattr_op_cnt
def test_deserialize_metadata_pickle(self): def test_deserialize_metadata_pickle(self):
@ -460,7 +457,6 @@ class TestUtils(unittest.TestCase):
xkey = _xkey(tf.name, utils.METADATA_KEY) xkey = _xkey(tf.name, utils.METADATA_KEY)
assert len(_xattrs.keys()) == 1 assert len(_xattrs.keys()) == 1
assert xkey in _xattrs assert xkey in _xattrs
assert _xattr_op_cnt['get'] == 1
assert _xattr_op_cnt['set'] == 1 assert _xattr_op_cnt['set'] == 1
md = deserialize_metadata(_xattrs[xkey]) md = deserialize_metadata(_xattrs[xkey])
assert r_md == md assert r_md == md
@ -482,7 +478,6 @@ class TestUtils(unittest.TestCase):
xkey = _xkey(td, utils.METADATA_KEY) xkey = _xkey(td, utils.METADATA_KEY)
assert len(_xattrs.keys()) == 1 assert len(_xattrs.keys()) == 1
assert xkey in _xattrs assert xkey in _xattrs
assert _xattr_op_cnt['get'] == 1
assert _xattr_op_cnt['set'] == 1 assert _xattr_op_cnt['set'] == 1
md = deserialize_metadata(_xattrs[xkey]) md = deserialize_metadata(_xattrs[xkey])
assert r_md == md assert r_md == md