Improving handling of file map cache

This commit is contained in:
Pavel Shevaev 2025-04-16 19:17:29 +03:00
parent 1b25beb4ed
commit 7b6d342469
3 changed files with 51 additions and 15 deletions

View File

@ -268,19 +268,30 @@ class ConfigCacheFileMap
return array_keys($this->file2deps[$file]);
}
function update(array $files)
function differs(array $files) : bool
{
$this_files = array_keys($this->file2deps);
return count($files) !== count($this_files) ||
count(array_intersect($files, $this_files)) != count($this_files);
}
function compare(array $files) : array
{
$this_files = array_keys($this->file2deps);
$added = array_diff($files, $this_files);
$removed = array_diff($this_files, $files);
return [$added, $removed];
}
function update(array $added, array $removed)
{
foreach($added as $file)
$this->file2deps[$file] = [];
foreach($removed as $file)
unset($this->file2deps[$file]);
return [$added, $removed];
}
function updateDepsForEntry(ConfigCacheEntry $entry)

View File

@ -15,7 +15,6 @@ class ConfigGlobals
public ?string $worker_init_fn = null;
public string $base_class = '\ConfBase';
public string $build_dir;
public ?ConfigCacheFileMap $file_map;
function __construct(array $base_dirs, string $build_dir, ?string $worker_init_fn = null)
{
@ -38,9 +37,9 @@ class ConfigGlobals
enum ConfigUpdateMode : int
{
case ChangedOnly = 1;
case Full = 1;
case RelativeToBundle = 2;
case Full = 3;
case ChangedOnly = 3;
}
class ConfigManager
@ -49,6 +48,7 @@ class ConfigManager
private int $workers_num;
private ConfigCache $cache;
private ?ConfigCacheFileMap $file_map;
function __construct(ConfigGlobals $globals, int $workers_num)
{
@ -56,6 +56,7 @@ class ConfigManager
$this->workers_num = $workers_num;
$this->cache = new ConfigCache($globals);
$this->file_map = null;
}
function getGlobals() : ConfigGlobals
@ -73,6 +74,18 @@ class ConfigManager
return [$this->globals->base_dirs, ['.js']];
}
function getFileMap() : ConfigCacheFileMap
{
if($this->file_map === null)
{
$map = $this->_tryLoadMap();
if($map === null)
$map = $this->_makeMap($this->scanFiles(extension: '.js'));
$this->file_map = $map;
}
return $this->file_map;
}
function updateCache(
ConfigUpdateMode $update_mode,
ConfigDirFiles $input_files = null,
@ -80,6 +93,8 @@ class ConfigManager
bool $verbose = false
) : ConfigCacheUpdateResult
{
config_log("Updating cache, mode {$update_mode->value}...");
if($input_files === null && $update_mode === ConfigUpdateMode::ChangedOnly)
throw new Exception("input_files argument is required for ChangedOnly mode");
@ -124,32 +139,33 @@ class ConfigManager
}
if($affected_files->count() > 0 || $added_files || $removed_files)
{
$fs_cache_map->update($added_files, $removed_files);
$this->_saveMap($fs_cache_map);
}
return $update_result;
}
private function _checkFileMap(ConfigUpdateMode $update_mode, ConfigDirFiles $input_files, array &$added_files, array &$removed_files) : ConfigCacheFileMap
{
//TODO: do we need to check if cache stale somehow?
$fs_cache_map = $this->_tryLoadMap();
$fs_cache_map = $this->file_map;
//NOTE: if there's no map so far we need to create one
if($fs_cache_map === null)
{
$fs_cache_map = new ConfigCacheFileMap();
//let's re-use the input files
if($update_mode === ConfigUpdateMode::Full || $update_mode === ConfigUpdateMode::RelativeToBundle)
$tmp_files = $input_files;
else
$tmp_files = $this->scanFiles(extension: '.js');
$fs_cache_map->update($tmp_files->getAllFiles());
$fs_cache_map = $this->_makeMap($tmp_files);
$this->file_map = $fs_cache_map;
}
if($update_mode === ConfigUpdateMode::Full || $update_mode === ConfigUpdateMode::RelativeToBundle)
{
list($added_files, $removed_files) = $fs_cache_map->update($input_files->getAllFiles());
list($added_files, $removed_files) = $fs_cache_map->compare($input_files->getAllFiles());
config_log("File map added: ".count($added_files).", removed: ".count($removed_files));
}
@ -193,7 +209,7 @@ class ConfigManager
{
$affected_by_file = $fs_cache_map->getAffectedFiles($file);
foreach($affected_by_file as $dep)
$affected_files->add(config_map_base_dir($this->globals->base_dirs, $dep), $dep, unique: true);
$affected_files->addFile($dep, unique: true);
}
else
{
@ -234,6 +250,15 @@ class ConfigManager
return ConfigCacheFileMap::unserialize(ensure_read($this->_getMapPath()));
}
private function _makeMap(ConfigDirFiles $files) : ConfigCacheFileMap
{
config_log("Creating file map");
$map = new ConfigCacheFileMap();
$map->update($files->getAllFiles(), []);
$this->_saveMap($map);
return $map;
}
private function _saveMap(ConfigCacheFileMap $map)
{
ensure_write($this->_getMapPath(), ConfigCacheFileMap::serialize($map));

View File

@ -12,8 +12,8 @@ class ConfigPackParams
public ?int $version = null;
public bool $debug = false;
public const string EXTRA_FMT3_CHUNK_SIZE = "EXTRA_FMT3_CHUNK_SIZE";
public const string EXTRA_FMT3_COMPRESSION_LEVEL = "EXTRA_FMT3_COMPRESSION_LEVEL";
public const EXTRA_FMT3_CHUNK_SIZE = "EXTRA_FMT3_CHUNK_SIZE";
public const EXTRA_FMT3_COMPRESSION_LEVEL = "EXTRA_FMT3_COMPRESSION_LEVEL";
public array $extras = array();
function __construct(