efrocache improvements work in progress

This commit is contained in:
Eric 2023-07-28 13:25:54 -07:00
parent b3a26cd8ab
commit 480f03c11d
No known key found for this signature in database
GPG Key ID: 89C93F0F8D6D5A98
21 changed files with 4228 additions and 4178 deletions

8248
.efrocachemap generated

File diff suppressed because it is too large Load Diff

View File

@ -3,6 +3,7 @@
<words> <words>
<w>_babase</w> <w>_babase</w>
<w>aaaa</w> <w>aaaa</w>
<w>aaaand</w>
<w>aaab</w> <w>aaab</w>
<w>aaac</w> <w>aaac</w>
<w>aaad</w> <w>aaad</w>
@ -1234,6 +1235,7 @@
<w>getobjs</w> <w>getobjs</w>
<w>getopt</w> <w>getopt</w>
<w>getplayer</w> <w>getplayer</w>
<w>getprojectconfig</w>
<w>getpt</w> <w>getpt</w>
<w>getr</w> <w>getr</w>
<w>getrefs</w> <w>getrefs</w>
@ -2443,6 +2445,7 @@
<w>reimported</w> <w>reimported</w>
<w>relfut</w> <w>relfut</w>
<w>relpath</w> <w>relpath</w>
<w>relurl</w>
<w>relwithdebinfo</w> <w>relwithdebinfo</w>
<w>remainingchecks</w> <w>remainingchecks</w>
<w>remoteapp</w> <w>remoteapp</w>
@ -2623,6 +2626,7 @@
<w>setmusic</w> <w>setmusic</w>
<w>setname</w> <w>setname</w>
<w>setnode</w> <w>setnode</w>
<w>setprojectconfig</w>
<w>setsticky</w> <w>setsticky</w>
<w>settingname</w> <w>settingname</w>
<w>setversion</w> <w>setversion</w>

View File

@ -1,5 +1,16 @@
### 1.7.25 (build 21202, api 8, 2023-07-28) ### 1.7.25 (build 21204, api 8, 2023-07-28)
- `getconfig` and `setconfig` in `efrotools` are now `getprojectconfig` and
`setprojectconfig` (to reflect the file name changes that happened in 1.7.20).
- The efrocache system (how assets and prebuilt binaries are downloaded during
builds) now uses a `efrocache_repository_url` value in
`config/projectconfig.json` instead of being hard-coded to my server. This
makes it possible to theoretically set up mirror servers. I currently keep the
cache pruned to the last few months worth of files but theoretically someone
could set up a server that never gets pruned and contains all history from now
until forever. Efrocache is basically just a big pile of files organized by
their hashes (see `tools/efrotools/efrocache.py` for details).
### 1.7.24 (build 21199, api 8, 2023-07-27) ### 1.7.24 (build 21199, api 8, 2023-07-27)
- Fixed an issue where respawn icons could disappear in epic mode (Thanks for - Fixed an issue where respawn icons could disappear in epic mode (Thanks for

View File

@ -3,6 +3,7 @@
<words> <words>
<w>NOMINMAX</w> <w>NOMINMAX</w>
<w>_babase</w> <w>_babase</w>
<w>aaaand</w>
<w>aabb</w> <w>aabb</w>
<w>aate</w> <w>aate</w>
<w>abcdefghijklmnopqrstuvwxyz</w> <w>abcdefghijklmnopqrstuvwxyz</w>
@ -745,6 +746,7 @@
<w>getpackagemodel</w> <w>getpackagemodel</w>
<w>getpackagesound</w> <w>getpackagesound</w>
<w>getpackagetexture</w> <w>getpackagetexture</w>
<w>getprojectconfig</w>
<w>getpublicpartyenabled</w> <w>getpublicpartyenabled</w>
<w>getpublicpartymaxsize</w> <w>getpublicpartymaxsize</w>
<w>getqrcodetexture</w> <w>getqrcodetexture</w>
@ -1444,6 +1446,7 @@
<w>reimported</w> <w>reimported</w>
<w>relfut</w> <w>relfut</w>
<w>reloadmedia</w> <w>reloadmedia</w>
<w>relurl</w>
<w>relwithdebinfo</w> <w>relwithdebinfo</w>
<w>rendererdata</w> <w>rendererdata</w>
<w>rendertarget</w> <w>rendertarget</w>
@ -1538,6 +1541,7 @@
<w>setdata</w> <w>setdata</w>
<w>setname</w> <w>setname</w>
<w>setnode</w> <w>setnode</w>
<w>setprojectconfig</w>
<w>setpublicpartyenabled</w> <w>setpublicpartyenabled</w>
<w>setpublicpartymaxsize</w> <w>setpublicpartymaxsize</w>
<w>setpublicpartyname</w> <w>setpublicpartyname</w>

View File

@ -18,6 +18,7 @@
"src/ballistica/base/platform/oculus/main_rift.cc", "src/ballistica/base/platform/oculus/main_rift.cc",
"src/ballistica/core/platform/android/android_gl3.c" "src/ballistica/core/platform/android/android_gl3.c"
], ],
"efrocache_repository_url": "https://files.ballistica.net/cache/ba1",
"name": "BallisticaKit", "name": "BallisticaKit",
"public": true, "public": true,
"pylint_ignored_untracked_deps": [ "pylint_ignored_untracked_deps": [

View File

@ -50,7 +50,7 @@ if TYPE_CHECKING:
# Build number and version of the ballistica binary we expect to be # Build number and version of the ballistica binary we expect to be
# using. # using.
TARGET_BALLISTICA_BUILD = 21202 TARGET_BALLISTICA_BUILD = 21204
TARGET_BALLISTICA_VERSION = '1.7.25' TARGET_BALLISTICA_VERSION = '1.7.25'

View File

@ -39,7 +39,7 @@ auto main(int argc, char** argv) -> int {
namespace ballistica { namespace ballistica {
// These are set automatically via script; don't modify them here. // These are set automatically via script; don't modify them here.
const int kEngineBuildNumber = 21202; const int kEngineBuildNumber = 21204;
const char* kEngineVersion = "1.7.25"; const char* kEngineVersion = "1.7.25";
#if BA_MONOLITHIC_BUILD #if BA_MONOLITHIC_BUILD

View File

@ -404,10 +404,10 @@ def generate_assets_makefile(
) -> dict[str, str]: ) -> dict[str, str]:
"""Main script entry point.""" """Main script entry point."""
# pylint: disable=too-many-locals # pylint: disable=too-many-locals
from efrotools import getconfig from efrotools import getprojectconfig
from pathlib import Path from pathlib import Path
public = getconfig(Path(projroot))['public'] public = getprojectconfig(Path(projroot))['public']
assert isinstance(public, bool) assert isinstance(public, bool)
original = existing_data original = existing_data

View File

@ -14,7 +14,7 @@ from typing import TYPE_CHECKING
from dataclasses import dataclass from dataclasses import dataclass
from efro.error import CleanError from efro.error import CleanError
from efrotools import getconfig from efrotools import getprojectconfig
if TYPE_CHECKING: if TYPE_CHECKING:
pass pass
@ -81,7 +81,7 @@ class MetaMakefileGenerator:
"""Do the thing.""" """Do the thing."""
# pylint: disable=too-many-locals # pylint: disable=too-many-locals
public = getconfig(Path(self._projroot))['public'] public = getprojectconfig(Path(self._projroot))['public']
assert isinstance(public, bool) assert isinstance(public, bool)
fname = 'src/meta/Makefile' fname = 'src/meta/Makefile'

View File

@ -446,9 +446,9 @@ def warm_start_asset_build() -> None:
import os import os
import subprocess import subprocess
from pathlib import Path from pathlib import Path
from efrotools import getconfig from efrotools import getprojectconfig
public: bool = getconfig(PROJROOT)['public'] public: bool = getprojectconfig(PROJROOT)['public']
if public: if public:
from efrotools.efrocache import warm_start_cache from efrotools.efrocache import warm_start_cache

View File

@ -9,7 +9,7 @@ from pathlib import Path
from typing import TYPE_CHECKING from typing import TYPE_CHECKING
from dataclasses import dataclass from dataclasses import dataclass
from efrotools import getconfig, getlocalconfig from efrotools import getprojectconfig, getlocalconfig
from efro.error import CleanError from efro.error import CleanError
from efro.terminal import Clr from efro.terminal import Clr
@ -60,7 +60,9 @@ class ProjectUpdater:
raise RuntimeError('fix and check cannot both be enabled') raise RuntimeError('fix and check cannot both be enabled')
# We behave a bit differently in the public repo. # We behave a bit differently in the public repo.
self.public: bool = getconfig(Path(projroot)).get('public', False) self.public: bool = getprojectconfig(Path(projroot)).get(
'public', False
)
assert isinstance(self.public, bool) assert isinstance(self.public, bool)
self._source_files: list[str] | None = None self._source_files: list[str] | None = None
@ -191,7 +193,7 @@ class ProjectUpdater:
if self.public: if self.public:
sources = [] sources = []
else: else:
sources = getconfig(Path(self.projroot)).get( sources = getprojectconfig(Path(self.projroot)).get(
'internal_source_files', [] 'internal_source_files', []
) )
if not isinstance(sources, list): if not isinstance(sources, list):
@ -209,7 +211,7 @@ class ProjectUpdater:
if self.public: if self.public:
sources = [] sources = []
else: else:
sources = getconfig(Path(self.projroot)).get( sources = getprojectconfig(Path(self.projroot)).get(
'internal_source_dirs', [] 'internal_source_dirs', []
) )
if not isinstance(sources, list): if not isinstance(sources, list):

View File

@ -57,9 +57,9 @@ class ResourcesMakefileGenerator:
existing_data: str, existing_data: str,
projname: str, projname: str,
) -> None: ) -> None:
from efrotools import getconfig from efrotools import getprojectconfig
self.public = getconfig(Path(projroot))['public'] self.public = getprojectconfig(Path(projroot))['public']
assert isinstance(self.public, bool) assert isinstance(self.public, bool)
self.existing_data = existing_data self.existing_data = existing_data
self.projroot = projroot self.projroot = projroot

View File

@ -15,7 +15,7 @@ from pathlib import Path
from typing import TYPE_CHECKING, assert_never from typing import TYPE_CHECKING, assert_never
from efrotools.code import format_python_str, format_cpp_str from efrotools.code import format_python_str, format_cpp_str
from efrotools import getconfig, replace_exact from efrotools import getprojectconfig, replace_exact
from efro.error import CleanError from efro.error import CleanError
from efro.terminal import Clr from efro.terminal import Clr
from efro.util import timedelta_str from efro.util import timedelta_str
@ -113,7 +113,7 @@ class SpinoffContext:
self._src_name = 'BallisticaKit' self._src_name = 'BallisticaKit'
self._public: bool = getconfig(Path(self._src_root))['public'] self._public: bool = getprojectconfig(Path(self._src_root))['public']
assert isinstance(self._public, bool) assert isinstance(self._public, bool)
self._src_all_feature_sets = { self._src_all_feature_sets = {

View File

@ -97,9 +97,9 @@ def _main() -> None:
elif cmd is Command.CREATE: elif cmd is Command.CREATE:
_do_create(src_root, dst_root) _do_create(src_root, dst_root)
elif cmd is Command.ADD_SUBMODULE_PARENT: elif cmd is Command.ADD_SUBMODULE_PARENT:
from efrotools import getconfig from efrotools import getprojectconfig
public = getconfig(Path(dst_root))['public'] public = getprojectconfig(Path(dst_root))['public']
_do_add_submodule_parent(dst_root, is_new=False, public=public) _do_add_submodule_parent(dst_root, is_new=False, public=public)
else: else:
assert_never(cmd) assert_never(cmd)
@ -130,7 +130,7 @@ def _do_create(src_root: str | None, dst_root: str) -> None:
# pylint: disable=too-many-locals, cyclic-import # pylint: disable=too-many-locals, cyclic-import
from efrotools import extract_arg, extract_flag from efrotools import extract_arg, extract_flag
from efrotools.code import format_python_str from efrotools.code import format_python_str
from efrotools import getconfig from efrotools import getprojectconfig
import batools.spinoff import batools.spinoff
# Note: in our case dst_root is actually what becomes the src project # Note: in our case dst_root is actually what becomes the src project
@ -204,7 +204,7 @@ def _do_create(src_root: str | None, dst_root: str) -> None:
# on git so its best to always do this. # on git so its best to always do this.
subprocess.run(['git', 'init'], cwd=path, check=True, capture_output=True) subprocess.run(['git', 'init'], cwd=path, check=True, capture_output=True)
public = getconfig(Path(dst_root))['public'] public = getprojectconfig(Path(dst_root))['public']
if submodule_parent: if submodule_parent:
_do_add_submodule_parent(path, is_new=True, public=public) _do_add_submodule_parent(path, is_new=True, public=public)

View File

@ -20,7 +20,7 @@ def spinoff_test(args: list[str]) -> None:
import subprocess import subprocess
from batools.featureset import FeatureSet from batools.featureset import FeatureSet
from efrotools import extract_flag, getconfig from efrotools import extract_flag, getprojectconfig
from efro.terminal import Clr from efro.terminal import Clr
from efro.error import CleanError from efro.error import CleanError
@ -31,7 +31,7 @@ def spinoff_test(args: list[str]) -> None:
"spinoff-test: can't pass both submodule parent" "spinoff-test: can't pass both submodule parent"
' and shared test parent.' ' and shared test parent.'
) )
public = getconfig(Path('.'))['public'] public = getprojectconfig(Path('.'))['public']
if shared_test_parent and public: if shared_test_parent and public:
raise CleanError('--shared-test-parent not available in public repo.') raise CleanError('--shared-test-parent not available in public repo.')

View File

@ -14,10 +14,10 @@ if TYPE_CHECKING:
def generate_top_level_makefile(projroot: str, existing_data: str) -> str: def generate_top_level_makefile(projroot: str, existing_data: str) -> str:
"""Main script entry point.""" """Main script entry point."""
from efrotools import getconfig from efrotools import getprojectconfig
from pathlib import Path from pathlib import Path
public = getconfig(Path(projroot))['public'] public = getprojectconfig(Path(projroot))['public']
assert isinstance(public, bool) assert isinstance(public, bool)
original = existing_data original = existing_data

View File

@ -34,7 +34,7 @@ def explicit_bool(value: bool) -> bool:
return value return value
def getlocalconfig(projroot: Path) -> dict[str, Any]: def getlocalconfig(projroot: Path | str) -> dict[str, Any]:
"""Return a project's localconfig contents (or default if missing).""" """Return a project's localconfig contents (or default if missing)."""
localconfig: dict[str, Any] localconfig: dict[str, Any]
@ -51,7 +51,7 @@ def getlocalconfig(projroot: Path) -> dict[str, Any]:
return localconfig return localconfig
def getconfig(projroot: Path) -> dict[str, Any]: def getprojectconfig(projroot: Path | str) -> dict[str, Any]:
"""Return a project's projectconfig contents (or default if missing).""" """Return a project's projectconfig contents (or default if missing)."""
config: dict[str, Any] config: dict[str, Any]
try: try:
@ -64,7 +64,7 @@ def getconfig(projroot: Path) -> dict[str, Any]:
return config return config
def setconfig(projroot: Path, config: dict[str, Any]) -> None: def setprojectconfig(projroot: Path | str, config: dict[str, Any]) -> None:
"""Set the project config contents.""" """Set the project config contents."""
os.makedirs(Path(projroot, 'config'), exist_ok=True) os.makedirs(Path(projroot, 'config'), exist_ok=True)
with Path(projroot, 'config/projectconfig.json').open( with Path(projroot, 'config/projectconfig.json').open(

View File

@ -138,7 +138,7 @@ def check_cpplint(projroot: Path, full: bool) -> None:
from concurrent.futures import ThreadPoolExecutor from concurrent.futures import ThreadPoolExecutor
from multiprocessing import cpu_count from multiprocessing import cpu_count
from efrotools import getconfig, PYVER from efrotools import getprojectconfig, PYVER
from efro.terminal import Clr from efro.terminal import Clr
os.chdir(projroot) os.chdir(projroot)
@ -148,7 +148,9 @@ def check_cpplint(projroot: Path, full: bool) -> None:
raise RuntimeError(f'Found space in path {fpath}; unexpected.') raise RuntimeError(f'Found space in path {fpath}; unexpected.')
# Check the config for a list of ones to ignore. # Check the config for a list of ones to ignore.
code_blacklist: list[str] = getconfig(projroot).get('cpplint_blacklist', []) code_blacklist: list[str] = getprojectconfig(projroot).get(
'cpplint_blacklist', []
)
# Just pretend blacklisted ones don't exist. # Just pretend blacklisted ones don't exist.
filenames = [f for f in filenames if f not in code_blacklist] filenames = [f for f in filenames if f not in code_blacklist]
@ -220,10 +222,10 @@ def get_code_filenames(projroot: Path, include_generated: bool) -> list[str]:
could cause dirty generated files to not get updated properly when could cause dirty generated files to not get updated properly when
their sources change). their sources change).
""" """
from efrotools import getconfig from efrotools import getprojectconfig
exts = ('.h', '.c', '.cc', '.cpp', '.cxx', '.m', '.mm') exts = ('.h', '.c', '.cc', '.cpp', '.cxx', '.m', '.mm')
places = getconfig(projroot).get('code_source_dirs', None) places = getprojectconfig(projroot).get('code_source_dirs', None)
if places is None: if places is None:
raise RuntimeError('code_source_dirs not declared in config') raise RuntimeError('code_source_dirs not declared in config')
codefilenames = [] codefilenames = []
@ -337,12 +339,12 @@ def _should_include_script(fnamefull: str) -> bool:
def get_script_filenames(projroot: Path) -> list[str]: def get_script_filenames(projroot: Path) -> list[str]:
"""Return the Python filenames to lint-check or auto-format.""" """Return the Python filenames to lint-check or auto-format."""
from efrotools import getconfig from efrotools import getprojectconfig
proot = f'{projroot}/' proot = f'{projroot}/'
filenames = set() filenames = set()
places = getconfig(projroot).get('python_source_dirs', None) places = getprojectconfig(projroot).get('python_source_dirs', None)
if places is None: if places is None:
raise RuntimeError('python_source_dirs not declared in config') raise RuntimeError('python_source_dirs not declared in config')
for place in places: for place in places:
@ -561,7 +563,7 @@ def _apply_pylint_run_to_cache(
from astroid import modutils from astroid import modutils
from efrotools import getconfig from efrotools import getprojectconfig
# First off, build a map of dirtyfiles to module names # First off, build a map of dirtyfiles to module names
# (and the corresponding reverse map). # (and the corresponding reverse map).
@ -609,7 +611,7 @@ def _apply_pylint_run_to_cache(
untracked_deps.add(mname) untracked_deps.add(mname)
ignored_untracked_deps: set[str] = set( ignored_untracked_deps: set[str] = set(
getconfig(projroot).get('pylint_ignored_untracked_deps', []) getprojectconfig(projroot).get('pylint_ignored_untracked_deps', [])
) )
# Add a few that this package itself triggers. # Add a few that this package itself triggers.

View File

@ -31,8 +31,6 @@ from efro.terminal import Clr
if TYPE_CHECKING: if TYPE_CHECKING:
pass pass
BASE_URL = 'https://files.ballistica.net/cache/ba1/'
TARGET_TAG = '# __EFROCACHE_TARGET__' TARGET_TAG = '# __EFROCACHE_TARGET__'
CACHE_DIR_NAME = '.efrocache' CACHE_DIR_NAME = '.efrocache'
@ -57,6 +55,21 @@ g_cache_prefix_noexec: bytes | None = None
g_cache_prefix_exec: bytes | None = None g_cache_prefix_exec: bytes | None = None
def get_repository_base_url() -> str:
"""Return the base repository url (assumes cwd is project root)."""
# from efrotools import getprojectconfig
import efrotools
pconfig = efrotools.getprojectconfig('.')
name = 'efrocache_repository_url'
val = pconfig.get(name)
if not isinstance(val, str):
raise RuntimeError(f"'{name}' was not found in projectconfig.")
if val.endswith('/'):
raise RuntimeError('Repository string should not end in a slash.')
return val
def get_existing_file_hash(path: str) -> str: def get_existing_file_hash(path: str) -> str:
"""Return the hash used for caching.""" """Return the hash used for caching."""
import hashlib import hashlib
@ -95,7 +108,15 @@ def get_target(path: str) -> None:
efrocachemap = json.loads(infile.read()) efrocachemap = json.loads(infile.read())
if path not in efrocachemap: if path not in efrocachemap:
raise RuntimeError(f'Path not found in efrocache: {path}') raise RuntimeError(f'Path not found in efrocache: {path}')
url = efrocachemap[path] relurl = efrocachemap[path]
# These used to be abs paths but are now relative.
assert not relurl.startswith('https:')
assert not relurl.startswith('/')
repo = get_repository_base_url()
url = f'{repo}/{relurl}'
subpath = '/'.join(url.split('/')[-3:]) subpath = '/'.join(url.split('/')[-3:])
local_cache_path = os.path.join(CACHE_DIR_NAME, subpath) local_cache_path = os.path.join(CACHE_DIR_NAME, subpath)
local_cache_path_dl = local_cache_path + '.download' local_cache_path_dl = local_cache_path + '.download'
@ -198,7 +219,7 @@ def filter_makefile(makefile_dir: str, contents: str) -> str:
lines = contents.splitlines() lines = contents.splitlines()
pcommand = 'tools/pcommand' pcommand = 'tools/pcommand'
# Replace cachable targets with cache lookups # Replace cachable targets with cache lookups.
while TARGET_TAG in lines: while TARGET_TAG in lines:
index = lines.index(TARGET_TAG) index = lines.index(TARGET_TAG)
endindex = index endindex = index
@ -378,14 +399,16 @@ def _write_cache_files(
with ThreadPoolExecutor(max_workers=cpu_count()) as executor: with ThreadPoolExecutor(max_workers=cpu_count()) as executor:
results = executor.map(call, fnames1) results = executor.map(call, fnames1)
for result in results: for result in results:
mapping[result[0]] = BASE_URL + result[1] # mapping[result[0]] = f'{base_url}/{result[1]}'
mapping[result[0]] = result[1]
fhashes1.add(result[1]) fhashes1.add(result[1])
# Now finish up with the second set. # Now finish up with the second set.
with ThreadPoolExecutor(max_workers=cpu_count()) as executor: with ThreadPoolExecutor(max_workers=cpu_count()) as executor:
results = executor.map(call, fnames2) results = executor.map(call, fnames2)
for result in results: for result in results:
mapping[result[0]] = BASE_URL + result[1] # mapping[result[0]] = f'{base_url}/result[1]'
mapping[result[0]] = result[1]
fhashes2.add(result[1]) fhashes2.add(result[1])
# We want the server to have a startercache.tar.xz file which # We want the server to have a startercache.tar.xz file which
@ -395,8 +418,8 @@ def _write_cache_files(
# upload that. # upload that.
# Also let's have the script touch both sets of files so we can use # Also let's have the script touch both sets of files so we can use
# mod-times to prune older files. (otherwise files that never change # mod-times to prune older files. Otherwise files that never change
# might have very old mod times) # might have very old mod times.
script = ( script = (
'import os\n' 'import os\n'
'import pathlib\n' 'import pathlib\n'
@ -508,6 +531,8 @@ def _check_warm_start_entries(entries: list[tuple[str, str]]) -> None:
def warm_start_cache() -> None: def warm_start_cache() -> None:
"""Run a pre-pass on the efrocache to improve efficiency.""" """Run a pre-pass on the efrocache to improve efficiency."""
base_url = get_repository_base_url()
# We maintain a starter-cache on the staging server, which is simply # We maintain a starter-cache on the staging server, which is simply
# the latest set of cache entries compressed into a single # the latest set of cache entries compressed into a single
# compressed archive. If we have no local cache yet we can download # compressed archive. If we have no local cache yet we can download
@ -518,7 +543,7 @@ def warm_start_cache() -> None:
if not os.path.exists(CACHE_DIR_NAME): if not os.path.exists(CACHE_DIR_NAME):
print('Downloading asset starter-cache...', flush=True) print('Downloading asset starter-cache...', flush=True)
subprocess.run( subprocess.run(
f'curl --fail {BASE_URL}startercache.tar.xz' f'curl --fail {base_url}/startercache.tar.xz'
f' --output startercache.tar.xz', f' --output startercache.tar.xz',
shell=True, shell=True,
check=True, check=True,

View File

@ -9,7 +9,7 @@ import subprocess
import sys import sys
from dataclasses import dataclass from dataclasses import dataclass
from efrotools import getlocalconfig, getconfig from efrotools import getprojectconfig, getlocalconfig
MODES = { MODES = {
'debug': {'configuration': 'Debug'}, 'debug': {'configuration': 'Debug'},
@ -59,7 +59,8 @@ def push_ipa(
from efrotools.xcodebuild import project_build_path from efrotools.xcodebuild import project_build_path
# Load both the local and project config data. # Load both the local and project config data.
cfg = Config(**getconfig(root)['push_ipa_config']) # FIXME: switch this to use dataclassio.
cfg = Config(**getprojectconfig(root)['push_ipa_config'])
lcfg = LocalConfig(**getlocalconfig(root)['push_ipa_local_config']) lcfg = LocalConfig(**getlocalconfig(root)['push_ipa_local_config'])
if modename not in MODES: if modename not in MODES:

View File

@ -491,7 +491,7 @@ def tool_config_install() -> None:
def _filter_tool_config(cfg: str) -> str: def _filter_tool_config(cfg: str) -> str:
import textwrap import textwrap
from efrotools import getconfig from efrotools import getprojectconfig
# Stick project-root wherever they want. # Stick project-root wherever they want.
cfg = cfg.replace('__EFRO_PROJECT_ROOT__', str(PROJROOT)) cfg = cfg.replace('__EFRO_PROJECT_ROOT__', str(PROJROOT))
@ -499,7 +499,7 @@ def _filter_tool_config(cfg: str) -> str:
# Stick a colon-separated list of project Python paths wherever they want. # Stick a colon-separated list of project Python paths wherever they want.
name = '__EFRO_PYTHON_PATHS__' name = '__EFRO_PYTHON_PATHS__'
if name in cfg: if name in cfg:
pypaths = getconfig(PROJROOT).get('python_paths') pypaths = getprojectconfig(PROJROOT).get('python_paths')
if pypaths is None: if pypaths is None:
raise RuntimeError('python_paths not set in project config') raise RuntimeError('python_paths not set in project config')
assert not any(' ' in p for p in pypaths) assert not any(' ' in p for p in pypaths)
@ -560,7 +560,7 @@ truthy-function, unused-awaitable
# Gen a pylint init hook which sets up our python paths. # Gen a pylint init hook which sets up our python paths.
pylint_init_tag = '__EFRO_PYLINT_INIT__' pylint_init_tag = '__EFRO_PYLINT_INIT__'
if pylint_init_tag in cfg: if pylint_init_tag in cfg:
pypaths = getconfig(PROJROOT).get('python_paths') pypaths = getprojectconfig(PROJROOT).get('python_paths')
if pypaths is None: if pypaths is None:
raise RuntimeError('python_paths not set in project config') raise RuntimeError('python_paths not set in project config')
cstr = 'init-hook=import sys;' cstr = 'init-hook=import sys;'
@ -633,14 +633,14 @@ def sync_all() -> None:
def sync() -> None: def sync() -> None:
"""Runs standard syncs between this project and others.""" """Runs standard syncs between this project and others."""
from efrotools import getconfig from efrotools import getprojectconfig
from efrotools.sync import Mode, SyncItem, run_standard_syncs from efrotools.sync import Mode, SyncItem, run_standard_syncs
mode = Mode(sys.argv[2]) if len(sys.argv) > 2 else Mode.PULL mode = Mode(sys.argv[2]) if len(sys.argv) > 2 else Mode.PULL
# Load sync-items from project config and run them # Load sync-items from project config and run them
sync_items = [ sync_items = [
SyncItem(**i) for i in getconfig(PROJROOT).get('sync_items', []) SyncItem(**i) for i in getprojectconfig(PROJROOT).get('sync_items', [])
] ]
run_standard_syncs(PROJROOT, mode, sync_items) run_standard_syncs(PROJROOT, mode, sync_items)
@ -674,11 +674,11 @@ def pytest() -> None:
import os import os
import platform import platform
import subprocess import subprocess
from efrotools import getconfig, PYTHON_BIN from efrotools import getprojectconfig, PYTHON_BIN
from efro.error import CleanError from efro.error import CleanError
# Grab our python paths for the project and stuff them in PYTHONPATH. # Grab our python paths for the project and stuff them in PYTHONPATH.
pypaths = getconfig(PROJROOT).get('python_paths') pypaths = getprojectconfig(PROJROOT).get('python_paths')
if pypaths is None: if pypaths is None:
raise CleanError('python_paths not found in project config.') raise CleanError('python_paths not found in project config.')