use commit hash as assets' version instead of dedicated version per file
This commit is contained in:
parent
93d0b6d09c
commit
1f2e75e6f4
2
.gitignore
vendored
2
.gitignore
vendored
@ -7,7 +7,7 @@ src/test.php
|
||||
.DS_Store
|
||||
._.DS_Store
|
||||
.sass-cache/
|
||||
config-static.php
|
||||
config-runtime.php
|
||||
/config.yaml
|
||||
/.idea
|
||||
/htdocs/dist-css
|
||||
|
6
Makefile
6
Makefile
@ -10,7 +10,7 @@ all:
|
||||
deploy:
|
||||
./deploy/deploy.sh
|
||||
|
||||
static: build-js build-css static-config
|
||||
static: build-js build-css runtime-config
|
||||
|
||||
build-js:
|
||||
./deploy/build_js.sh -i ./htdocs/js -o ./htdocs/dist-js
|
||||
@ -18,5 +18,5 @@ build-js:
|
||||
build-css:
|
||||
./deploy/build_css.sh -i ./htdocs/scss -o ./htdocs/dist-css
|
||||
|
||||
static-config:
|
||||
./deploy/gen_static_config.php -i ./htdocs > ./config-static.php
|
||||
runtime-config:
|
||||
./deploy/gen_runtime_config.php -i ./htdocs > ./config-runtime.php
|
||||
|
@ -41,7 +41,9 @@ cp "$DEV_DIR/config.yaml" .
|
||||
|
||||
"$DIR"/build_js.sh -i "$DEV_DIR/htdocs/js" -o "$STAGING_DIR/htdocs/dist-js" || die "build_js failed"
|
||||
"$DIR"/build_css.sh -i "$DEV_DIR/htdocs/scss" -o "$STAGING_DIR/htdocs/dist-css" || die "build_css failed"
|
||||
$PHP "$DIR"/gen_static_config.php -i "$STAGING_DIR/htdocs" > "$STAGING_DIR/config-static.php" || die "gen_static_config failed"
|
||||
$PHP "$DIR"/gen_runtime_config.php \
|
||||
--htdocs-dir "$STAGING_DIR/htdocs" \
|
||||
--commit-hash "$(git rev-parse --short=8 HEAD)" > "$STAGING_DIR/config-runtime.php" || die "gen_runtime_config failed"
|
||||
|
||||
cd "$DIR"
|
||||
|
||||
|
@ -1,67 +1,57 @@
|
||||
#!/usr/bin/env php
|
||||
<?php
|
||||
|
||||
use app\CliUtil;
|
||||
|
||||
require __DIR__.'/../src/init.php';
|
||||
|
||||
if ($argc <= 1) {
|
||||
usage();
|
||||
exit(1);
|
||||
}
|
||||
$htdocs_dir = null;
|
||||
$commit_hash = null;
|
||||
for ($i = 1; $i < $argc; $i++) {
|
||||
switch ($argv[$i]) {
|
||||
case '--htdocs-dir':
|
||||
$htdocs_dir = $argv[++$i] ?? usage('missing value for --htdocs-dir');
|
||||
break;
|
||||
|
||||
$input_dir = null;
|
||||
|
||||
array_shift($argv);
|
||||
while (count($argv) > 0) {
|
||||
switch ($argv[0]) {
|
||||
case '-i':
|
||||
array_shift($argv);
|
||||
$input_dir = array_shift($argv);
|
||||
case '--commit-hash':
|
||||
$commit_hash = $argv[++$i] ?? usage('missing value for --commit-hash');
|
||||
break;
|
||||
|
||||
default:
|
||||
CliUtil::die('unsupported argument: '.$argv[0]);
|
||||
usage("unknown option {$argv[$i]}");
|
||||
}
|
||||
}
|
||||
|
||||
if (is_null($input_dir))
|
||||
CliUtil::die("input directory has not been specified");
|
||||
if (is_null($htdocs_dir) || is_null($commit_hash))
|
||||
usage();
|
||||
|
||||
$hashes = [];
|
||||
$hashes = [
|
||||
'commit_hash' => $commit_hash,
|
||||
'assets' => []
|
||||
];
|
||||
foreach (['css', 'js'] as $type) {
|
||||
$entries = glob_recursive($input_dir.'/dist-'.$type.'/*.'.$type);
|
||||
$entries = glob_recursive($htdocs_dir.'/dist-'.$type.'/*.'.$type);
|
||||
if (empty($entries)) {
|
||||
CliUtil::error("warning: no files found in $input_dir/dist-$type");
|
||||
fwrite(STDERR, "warning: no files found in $htdocs_dir/dist-$type\n");
|
||||
continue;
|
||||
}
|
||||
|
||||
foreach ($entries as $file) {
|
||||
$hashes[$type.'/'.basename($file)] = [
|
||||
'version' => get_hash($file),
|
||||
$hashes['assets'][$type.'/'.basename($file)] = [
|
||||
'integrity' => []
|
||||
];
|
||||
foreach (\engine\skin\FeaturedSkin::RESOURCE_INTEGRITY_HASHES as $hash_type)
|
||||
$hashes[$type.'/'.basename($file)]['integrity'][$hash_type] = base64_encode(hash_file($hash_type, $file, true));
|
||||
$hashes['assets'][$type.'/'.basename($file)]['integrity'][$hash_type] = base64_encode(hash_file($hash_type, $file, true));
|
||||
}
|
||||
}
|
||||
|
||||
echo "<?php\n\n";
|
||||
echo "return ".var_export($hashes, true).";\n";
|
||||
|
||||
function usage(): void {
|
||||
global $argv;
|
||||
echo <<<EOF
|
||||
usage: {$argv[0]} [OPTIONS]
|
||||
|
||||
Options:
|
||||
-i input htdocs directory
|
||||
|
||||
EOF;
|
||||
}
|
||||
|
||||
function get_hash(string $path): string {
|
||||
return substr(sha1(file_get_contents($path)), 0, 8);
|
||||
function usage(string $msg = ''): never {
|
||||
if ($msg !== '')
|
||||
fwrite(STDERR, "error: {$msg}\n");
|
||||
$script = $GLOBALS['argv'][0];
|
||||
fwrite(STDERR, "usage: {$script} --htdocs_dir DIR --commit-hash HASH\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
function glob_escape(string $pattern): string {
|
@ -10,10 +10,17 @@ var StaticManager = {
|
||||
versions: {},
|
||||
|
||||
/**
|
||||
* @type {string}
|
||||
*/
|
||||
commitHash: '',
|
||||
|
||||
/**
|
||||
* @param {string} commitHash
|
||||
* @param {string[]} loadedStyles
|
||||
* @param {object} versions
|
||||
*/
|
||||
init: function(loadedStyles, versions) {
|
||||
init: function(commitHash, loadedStyles, versions) {
|
||||
this.commitHash = commitHash;
|
||||
this.loadedStyles = loadedStyles;
|
||||
this.versions = versions;
|
||||
},
|
||||
@ -28,7 +35,7 @@ var StaticManager = {
|
||||
if (!window.appConfig.devMode) {
|
||||
if (theme === 'dark')
|
||||
name += '_dark';
|
||||
url = '/dist-css/'+name+'.css?v='+this.versions.css[name].version;
|
||||
url = '/dist-css/'+name+'.css?v='+this.commitHash;
|
||||
id = 'style_'+name;
|
||||
} else {
|
||||
url = '/sass.php?name='+name+'&theme='+theme+'&v='+timestamp();
|
||||
|
@ -205,13 +205,13 @@ HTML;
|
||||
$versions = '{}';
|
||||
else {
|
||||
$versions = [];
|
||||
foreach ($config['static'] as $name => $v) {
|
||||
foreach ($config['assets'] as $name => $v) {
|
||||
list($type, $bname) = $this->getStaticNameParts($name);
|
||||
$versions[$type][$bname] = $v;
|
||||
}
|
||||
$versions = jsonEncode($versions);
|
||||
}
|
||||
$html .= 'StaticManager.init('.jsonEncode($this->styleNames).', '.$versions.');';
|
||||
$html .= 'StaticManager.init(\''.$config['commit_hash'].'\', '.jsonEncode($this->styleNames).', '.$versions.');';
|
||||
$html .= 'ThemeSwitcher.init();';
|
||||
|
||||
if (!empty($this->exportedStrings)) {
|
||||
@ -230,16 +230,18 @@ HTML;
|
||||
}
|
||||
|
||||
protected function jsLink(string $name): string {
|
||||
global $config;
|
||||
list (, $bname) = $this->getStaticNameParts($name);
|
||||
if (isDev()) {
|
||||
$href = '/js.php?name='.urlencode($bname).'&v='.time();
|
||||
} else {
|
||||
$href = '/dist-js/'.$bname.'.js?v='.$this->getStaticVersion($name);
|
||||
$href = '/dist-js/'.$bname.'.js?v='.$config['commit_hash'];
|
||||
}
|
||||
return '<script src="'.$href.'" type="text/javascript"'.$this->getStaticIntegrityAttribute($name).'></script>';
|
||||
}
|
||||
|
||||
protected function cssLink(string $name, string $theme, &$bname = null): string {
|
||||
global $config;
|
||||
list(, $bname) = $this->getStaticNameParts($name);
|
||||
|
||||
$config_name = 'css/'.$bname.($theme == 'dark' ? '_dark' : '').'.css';
|
||||
@ -247,8 +249,7 @@ HTML;
|
||||
if (isDev()) {
|
||||
$href = '/sass.php?name='.urlencode($bname).'&theme='.$theme.'&v='.time();
|
||||
} else {
|
||||
$version = $this->getStaticVersion($config_name);
|
||||
$href = '/dist-css/'.$bname.($theme == 'dark' ? '_dark' : '').'.css?v='.$version;
|
||||
$href = '/dist-css/'.$bname.($theme == 'dark' ? '_dark' : '').'.css?v='.$config['commit_hash'];
|
||||
}
|
||||
|
||||
$id = 'style_'.$bname;
|
||||
@ -259,7 +260,8 @@ HTML;
|
||||
}
|
||||
|
||||
protected function cssPrefetchLink(string $name): string {
|
||||
$url = '/dist-css/'.$name.'.css?v='.$this->getStaticVersion('css/'.$name.'.css');
|
||||
global $config;
|
||||
$url = '/dist-css/'.$name.'.css?v='.$config['commit_hash'];
|
||||
$integrity = $this->getStaticIntegrityAttribute('css/'.$name.'.css');
|
||||
return '<link rel="prefetch" href="'.$url.'"'.$integrity.' />';
|
||||
}
|
||||
@ -276,21 +278,10 @@ HTML;
|
||||
return [$dname, $bname, $ext];
|
||||
}
|
||||
|
||||
protected function getStaticVersion(string $name): string {
|
||||
global $config;
|
||||
if (isDev())
|
||||
return time();
|
||||
if (str_starts_with($name, '/')) {
|
||||
logWarning(__FUNCTION__.': '.$name.' starts with /');
|
||||
$name = substr($name, 1);
|
||||
}
|
||||
return $config['static'][$name]['version'] ?? 'notfound';
|
||||
}
|
||||
|
||||
protected function getStaticIntegrityAttribute(string $name): string {
|
||||
if (isDev())
|
||||
return '';
|
||||
global $config;
|
||||
return ' integrity="'.implode(' ', array_map(fn($hash_type) => $hash_type.'-'.$config['static'][$name]['integrity'][$hash_type], self::RESOURCE_INTEGRITY_HASHES)).'"';
|
||||
return ' integrity="'.implode(' ', array_map(fn($hash_type) => $hash_type.'-'.$config['assets'][$name]['integrity'][$hash_type], self::RESOURCE_INTEGRITY_HASHES)).'"';
|
||||
}
|
||||
}
|
@ -57,10 +57,10 @@ $globalContext->setLogger($logger);
|
||||
unset($logger);
|
||||
|
||||
if (!isDev()) {
|
||||
if (file_exists(APP_ROOT.'/config-static.php'))
|
||||
$config['static'] = require_once 'config-static.php';
|
||||
if (file_exists(APP_ROOT.'/config-runtime.php'))
|
||||
$config += require_once 'config-runtime.php';
|
||||
else
|
||||
die('config-static.php not found');
|
||||
die('config-runtime.php not found');
|
||||
|
||||
// turn off errors output on production domains
|
||||
error_reporting(0);
|
||||
|
Loading…
x
Reference in New Issue
Block a user