Changeset - 33cb734b19d0
[Not reviewed]
0 2 0
Brett Smith - 4 years ago 2020-03-27 14:55:30
brettcsmith@brettcsmith.org
config: Create cache database files with 0o600 mode.

I wasn't too worried about this earlier because the cache mainly stores
a bunch of numbers, but there's a little more than that: the generated
URLs also include original attachment filenames, which might be sensitive
(referencing people's names, bank names, etc.). Tighten security
accordingly.
2 files changed with 20 insertions and 3 deletions:
0 comments (0 inline, 0 general)
conservancy_beancount/config.py
Show inline comments
...
 
@@ -134,7 +134,13 @@ class Config:
 
                credentials.user,
 
                urlparse.quote(str(credentials.server), ''),
 
            )
 
            cache_db = rtutil.RTLinkCache.setup(cache_dir_path / cache_name)
 
            cache_path = cache_dir_path / cache_name
 
            try:
 
                cache_path.touch(0o600)
 
            except OSError:
 
                # RTLinkCache.setup() will handle the problem.
 
                pass
 
            cache_db = rtutil.RTLinkCache.setup(cache_path)
 
        return rtutil.RT(wrapper_client, cache_db)
 

	
 
    def rt_wrapper(self,
tests/test_config.py
Show inline comments
...
 
@@ -74,6 +74,14 @@ def update_environ(**kwargs):
 
    finally:
 
        _update_environ(revert)
 

	
 
@contextlib.contextmanager
 
def update_umask(mask):
 
    old_mask = os.umask(mask)
 
    try:
 
        yield old_mask
 
    finally:
 
        os.umask(old_mask)
 

	
 
def test_repository_from_environment():
 
    config = config_mod.Config()
 
    assert config.repository_path() == testutil.test_path('repository')
...
 
@@ -208,12 +216,15 @@ def test_rt_wrapper_cache_responds_to_external_credential_changes(rt_environ):
 
    assert rt1 is not rt2
 

	
 
def test_rt_wrapper_has_cache(tmp_path):
 
    with update_environ(XDG_CACHE_DIR=tmp_path):
 
    with update_environ(XDG_CACHE_DIR=tmp_path), update_umask(0o002):
 
        config = config_mod.Config()
 
        rt = config.rt_wrapper(None, testutil.RTClient)
 
        rt.exists(1)
 
    expected = 'conservancy_beancount/{}@*.sqlite3'.format(RT_FILE_CREDS[1])
 
    assert any(tmp_path.glob(expected))
 
    actual = None
 
    for actual in tmp_path.glob(expected):
 
        assert not actual.stat().st_mode & 0o177
 
    assert actual is not None, "did not find any generated cache file"
 

	
 
def test_rt_wrapper_without_cache(tmp_path):
 
    tmp_path.chmod(0)
0 comments (0 inline, 0 general)