feat: minor improved security measures
This commit is contained in:
parent
27d7a4e6b5
commit
d1b2117fa2
3 changed files with 29 additions and 11 deletions
|
|
@ -56,8 +56,11 @@ function M.load()
|
||||||
end
|
end
|
||||||
|
|
||||||
if vim.fn.filereadable(cache_file) == 0 then
|
if vim.fn.filereadable(cache_file) == 0 then
|
||||||
vim.fn.writefile({}, cache_file)
|
vim.fn.mkdir(vim.fn.fnamemodify(cache_file, ':h'), 'p')
|
||||||
vim.fn.setfperm(cache_file, 'rw-------')
|
local tmpfile = vim.fn.tempname()
|
||||||
|
vim.fn.writefile({}, tmpfile)
|
||||||
|
vim.fn.setfperm(tmpfile, 'rw-------')
|
||||||
|
vim.uv.fs_rename(tmpfile, cache_file)
|
||||||
loaded = true
|
loaded = true
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
|
|
@ -107,8 +110,10 @@ function M.save()
|
||||||
cache_data._version = CACHE_VERSION
|
cache_data._version = CACHE_VERSION
|
||||||
local encoded = vim.json.encode(cache_data)
|
local encoded = vim.json.encode(cache_data)
|
||||||
local lines = vim.split(encoded, '\n')
|
local lines = vim.split(encoded, '\n')
|
||||||
vim.fn.writefile(lines, cache_file)
|
local tmpfile = vim.fn.tempname()
|
||||||
vim.fn.setfperm(cache_file, 'rw-------')
|
vim.fn.writefile(lines, tmpfile)
|
||||||
|
vim.fn.setfperm(tmpfile, 'rw-------')
|
||||||
|
vim.uv.fs_rename(tmpfile, cache_file)
|
||||||
end)
|
end)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -120,8 +120,10 @@ function M.logout(platform)
|
||||||
local ok, data = pcall(vim.fn.json_decode, vim.fn.readfile(cookie_file, 'b'))
|
local ok, data = pcall(vim.fn.json_decode, vim.fn.readfile(cookie_file, 'b'))
|
||||||
if ok and type(data) == 'table' then
|
if ok and type(data) == 'table' then
|
||||||
data[platform] = nil
|
data[platform] = nil
|
||||||
vim.fn.writefile({ vim.fn.json_encode(data) }, cookie_file)
|
local tmpfile = vim.fn.tempname()
|
||||||
vim.fn.setfperm(cookie_file, 'rw-------')
|
vim.fn.writefile({ vim.fn.json_encode(data) }, tmpfile)
|
||||||
|
vim.fn.setfperm(tmpfile, 'rw-------')
|
||||||
|
vim.uv.fs_rename(tmpfile, cookie_file)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
logger.log(display .. ' credentials cleared', { level = vim.log.levels.INFO, override = true })
|
logger.log(display .. ' credentials cleared', { level = vim.log.levels.INFO, override = true })
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,7 @@ import json
|
||||||
import os
|
import os
|
||||||
import re
|
import re
|
||||||
import sys
|
import sys
|
||||||
|
import tempfile
|
||||||
from abc import ABC, abstractmethod
|
from abc import ABC, abstractmethod
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from typing import Any
|
from typing import Any
|
||||||
|
|
@ -20,6 +21,18 @@ from .models import (
|
||||||
_COOKIE_FILE = Path.home() / ".cache" / "cp-nvim" / "cookies.json"
|
_COOKIE_FILE = Path.home() / ".cache" / "cp-nvim" / "cookies.json"
|
||||||
|
|
||||||
|
|
||||||
|
def _atomic_write(path: Path, content: str) -> None:
|
||||||
|
fd, tmp = tempfile.mkstemp(dir=path.parent, prefix=".tmp-")
|
||||||
|
try:
|
||||||
|
os.fchmod(fd, 0o600)
|
||||||
|
with os.fdopen(fd, "w") as f:
|
||||||
|
f.write(content)
|
||||||
|
os.replace(tmp, path)
|
||||||
|
except BaseException:
|
||||||
|
os.unlink(tmp)
|
||||||
|
raise
|
||||||
|
|
||||||
|
|
||||||
def load_platform_cookies(platform: str) -> Any | None:
|
def load_platform_cookies(platform: str) -> Any | None:
|
||||||
try:
|
try:
|
||||||
data = json.loads(_COOKIE_FILE.read_text())
|
data = json.loads(_COOKIE_FILE.read_text())
|
||||||
|
|
@ -29,22 +42,20 @@ def load_platform_cookies(platform: str) -> Any | None:
|
||||||
|
|
||||||
|
|
||||||
def save_platform_cookies(platform: str, data: Any) -> None:
|
def save_platform_cookies(platform: str, data: Any) -> None:
|
||||||
_COOKIE_FILE.parent.mkdir(parents=True, exist_ok=True)
|
_COOKIE_FILE.parent.mkdir(parents=True, exist_ok=True, mode=0o700)
|
||||||
try:
|
try:
|
||||||
existing = json.loads(_COOKIE_FILE.read_text())
|
existing = json.loads(_COOKIE_FILE.read_text())
|
||||||
except Exception:
|
except Exception:
|
||||||
existing = {}
|
existing = {}
|
||||||
existing[platform] = data
|
existing[platform] = data
|
||||||
_COOKIE_FILE.write_text(json.dumps(existing))
|
_atomic_write(_COOKIE_FILE, json.dumps(existing))
|
||||||
_COOKIE_FILE.chmod(0o600)
|
|
||||||
|
|
||||||
|
|
||||||
def clear_platform_cookies(platform: str) -> None:
|
def clear_platform_cookies(platform: str) -> None:
|
||||||
try:
|
try:
|
||||||
existing = json.loads(_COOKIE_FILE.read_text())
|
existing = json.loads(_COOKIE_FILE.read_text())
|
||||||
existing.pop(platform, None)
|
existing.pop(platform, None)
|
||||||
_COOKIE_FILE.write_text(json.dumps(existing))
|
_atomic_write(_COOKIE_FILE, json.dumps(existing))
|
||||||
_COOKIE_FILE.chmod(0o600)
|
|
||||||
except Exception:
|
except Exception:
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue