adding checks for cross-featureset imports

This commit is contained in:
Eric 2023-06-12 11:30:09 -07:00
parent 2de0bed496
commit 1479395ec0
No known key found for this signature in database
GPG Key ID: 89C93F0F8D6D5A98
14 changed files with 304 additions and 151 deletions

56
.efrocachemap generated
View File

@ -4072,26 +4072,26 @@
"build/assets/workspace/ninjafightplug.py": "https://files.ballistica.net/cache/ba1/18/4b/787a9267e17be3c49966072581a5",
"build/assets/workspace/onslaughtplug.py": "https://files.ballistica.net/cache/ba1/20/f6/4ce9bc3c1f3732f6adf8237fbe9b",
"build/assets/workspace/runaroundplug.py": "https://files.ballistica.net/cache/ba1/a5/30/9058181df0b1255bf6950cbc7813",
"build/prefab/full/linux_arm64_gui/debug/ballisticakit": "https://files.ballistica.net/cache/ba1/f2/dc/bf56d88353b11986373e899b5bf6",
"build/prefab/full/linux_arm64_gui/release/ballisticakit": "https://files.ballistica.net/cache/ba1/3c/43/731228e0f7c8e5396b06ca916ffd",
"build/prefab/full/linux_arm64_server/debug/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/71/24/b8bedec2fab3fd83381a23385a9a",
"build/prefab/full/linux_arm64_server/release/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/5f/96/a43273ad50d90d9342f45c22c0e8",
"build/prefab/full/linux_x86_64_gui/debug/ballisticakit": "https://files.ballistica.net/cache/ba1/c9/75/393357c2a3f4d3eec2035bc3ecff",
"build/prefab/full/linux_x86_64_gui/release/ballisticakit": "https://files.ballistica.net/cache/ba1/b0/85/d8778105cf5a536cb5e6e618c723",
"build/prefab/full/linux_x86_64_server/debug/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/e8/41/5128ac78c21f238d0613ab8e2ece",
"build/prefab/full/linux_x86_64_server/release/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/7f/4d/96dadaf30683f4a69426518ca334",
"build/prefab/full/mac_arm64_gui/debug/ballisticakit": "https://files.ballistica.net/cache/ba1/14/14/9f38fb471edd66d076b9d611ba55",
"build/prefab/full/mac_arm64_gui/release/ballisticakit": "https://files.ballistica.net/cache/ba1/12/37/d741089b132fbcb8b22d9795479a",
"build/prefab/full/mac_arm64_server/debug/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/b0/4f/e9ab4d8fc7405d9c8f667eaacb73",
"build/prefab/full/mac_arm64_server/release/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/7e/2f/2e475906c60e960a63fdd3e5f24d",
"build/prefab/full/mac_x86_64_gui/debug/ballisticakit": "https://files.ballistica.net/cache/ba1/34/48/662a2168751cd25eaae50f0707df",
"build/prefab/full/mac_x86_64_gui/release/ballisticakit": "https://files.ballistica.net/cache/ba1/1d/2f/ab1c77b292726178d0eb1f5699ad",
"build/prefab/full/mac_x86_64_server/debug/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/44/b8/3c6e810fa14f014b9c91db7ab88a",
"build/prefab/full/mac_x86_64_server/release/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/14/59/2164e23d78a6b16a97b3bfe7bdb2",
"build/prefab/full/windows_x86_gui/debug/BallisticaKit.exe": "https://files.ballistica.net/cache/ba1/4f/91/83fa21e46183f74300820e98f4a1",
"build/prefab/full/windows_x86_gui/release/BallisticaKit.exe": "https://files.ballistica.net/cache/ba1/61/f5/18b5f9055fb48a1c91ce25f45dee",
"build/prefab/full/windows_x86_server/debug/dist/BallisticaKitHeadless.exe": "https://files.ballistica.net/cache/ba1/87/53/556e49d3273d4be8bfeba546ecb8",
"build/prefab/full/windows_x86_server/release/dist/BallisticaKitHeadless.exe": "https://files.ballistica.net/cache/ba1/98/9b/73c254c31fe68fc21cae40a1761e",
"build/prefab/full/linux_arm64_gui/debug/ballisticakit": "https://files.ballistica.net/cache/ba1/dd/e6/324379d12d8773f739bbc1ee8742",
"build/prefab/full/linux_arm64_gui/release/ballisticakit": "https://files.ballistica.net/cache/ba1/78/24/27722a657784f579f5824b089691",
"build/prefab/full/linux_arm64_server/debug/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/83/df/eabeb7b26fb4b5bf8b899ebcd067",
"build/prefab/full/linux_arm64_server/release/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/0a/99/6e19e6ad69a6f0fb4b73cacdd8e5",
"build/prefab/full/linux_x86_64_gui/debug/ballisticakit": "https://files.ballistica.net/cache/ba1/ad/bd/2f23197da76c148e41b359f0022a",
"build/prefab/full/linux_x86_64_gui/release/ballisticakit": "https://files.ballistica.net/cache/ba1/29/29/2a87524a909d447f938762919de4",
"build/prefab/full/linux_x86_64_server/debug/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/71/de/0b68a02b52ee2c5d356343dccd00",
"build/prefab/full/linux_x86_64_server/release/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/ea/22/0f260a3a44e4cfdf7706705c81a1",
"build/prefab/full/mac_arm64_gui/debug/ballisticakit": "https://files.ballistica.net/cache/ba1/58/1e/023f58fe727fc70ade8ae6d5a880",
"build/prefab/full/mac_arm64_gui/release/ballisticakit": "https://files.ballistica.net/cache/ba1/1e/50/a607cd2582de36c989f0d470658e",
"build/prefab/full/mac_arm64_server/debug/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/81/e2/d816ac2f91de53683636bf3144bd",
"build/prefab/full/mac_arm64_server/release/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/39/8e/756a7cc3ddcecd1146ea4589bf72",
"build/prefab/full/mac_x86_64_gui/debug/ballisticakit": "https://files.ballistica.net/cache/ba1/3c/ad/dcabf1359a1cae7c683036b23856",
"build/prefab/full/mac_x86_64_gui/release/ballisticakit": "https://files.ballistica.net/cache/ba1/f9/06/3b9d1661d6e4cc21c42748db322b",
"build/prefab/full/mac_x86_64_server/debug/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/cb/89/a4a0de5aaa1e1929871973587ddd",
"build/prefab/full/mac_x86_64_server/release/dist/ballisticakit_headless": "https://files.ballistica.net/cache/ba1/7a/3b/35ea440785a5ac39cb802b159c8a",
"build/prefab/full/windows_x86_gui/debug/BallisticaKit.exe": "https://files.ballistica.net/cache/ba1/53/9b/817e65aebfe3574d50385a08be52",
"build/prefab/full/windows_x86_gui/release/BallisticaKit.exe": "https://files.ballistica.net/cache/ba1/84/b0/70de1c4c94a2c1c8d1fe54da695f",
"build/prefab/full/windows_x86_server/debug/dist/BallisticaKitHeadless.exe": "https://files.ballistica.net/cache/ba1/ba/ec/009c2ead7a78de11c0e55e447881",
"build/prefab/full/windows_x86_server/release/dist/BallisticaKitHeadless.exe": "https://files.ballistica.net/cache/ba1/1f/8d/cdfe64de06a6861c27828b9120e8",
"build/prefab/lib/linux_arm64_gui/debug/libballistica_plus.a": "https://files.ballistica.net/cache/ba1/29/dc/e5b08aae2dbe3222082aaa1e90e7",
"build/prefab/lib/linux_arm64_gui/release/libballistica_plus.a": "https://files.ballistica.net/cache/ba1/ce/bb/5796a83ce9d1c9cf58e08f3ff351",
"build/prefab/lib/linux_arm64_server/debug/libballistica_plus.a": "https://files.ballistica.net/cache/ba1/31/65/014221e46f7974f40aa84c8922dc",
@ -4108,14 +4108,14 @@
"build/prefab/lib/mac_x86_64_gui/release/libballistica_plus.a": "https://files.ballistica.net/cache/ba1/14/4b/68a0ece3c1f191183b695cf45a4d",
"build/prefab/lib/mac_x86_64_server/debug/libballistica_plus.a": "https://files.ballistica.net/cache/ba1/1f/3f/d899a46cc0dc8bc4f1b38f9318a5",
"build/prefab/lib/mac_x86_64_server/release/libballistica_plus.a": "https://files.ballistica.net/cache/ba1/de/99/95fdcb3f614a7b83ada148bca38d",
"build/prefab/lib/windows/Debug_Win32/BallisticaKitGenericPlus.lib": "https://files.ballistica.net/cache/ba1/74/cb/8be4f4dec7fd2bf11920a48c5446",
"build/prefab/lib/windows/Debug_Win32/BallisticaKitGenericPlus.pdb": "https://files.ballistica.net/cache/ba1/ee/30/7d0a59834145150a5a64d29f2add",
"build/prefab/lib/windows/Debug_Win32/BallisticaKitHeadlessPlus.lib": "https://files.ballistica.net/cache/ba1/ad/53/a20f19509c6f90472c46004618e7",
"build/prefab/lib/windows/Debug_Win32/BallisticaKitHeadlessPlus.pdb": "https://files.ballistica.net/cache/ba1/d7/20/8311a232ef822de08b7eea1185e5",
"build/prefab/lib/windows/Release_Win32/BallisticaKitGenericPlus.lib": "https://files.ballistica.net/cache/ba1/f9/bb/cfb390d5f9d37997cacc804ee7ae",
"build/prefab/lib/windows/Release_Win32/BallisticaKitGenericPlus.pdb": "https://files.ballistica.net/cache/ba1/a6/fa/5651f4f3329109515ad15fbf7fbc",
"build/prefab/lib/windows/Release_Win32/BallisticaKitHeadlessPlus.lib": "https://files.ballistica.net/cache/ba1/d8/49/3f000f69e2b50364b7d444f90b3f",
"build/prefab/lib/windows/Release_Win32/BallisticaKitHeadlessPlus.pdb": "https://files.ballistica.net/cache/ba1/7b/bd/aff34983fc5a00bfb59fd47d14cb",
"build/prefab/lib/windows/Debug_Win32/BallisticaKitGenericPlus.lib": "https://files.ballistica.net/cache/ba1/52/08/03398c2a3fcc29a99c687d5efbb4",
"build/prefab/lib/windows/Debug_Win32/BallisticaKitGenericPlus.pdb": "https://files.ballistica.net/cache/ba1/e8/85/12943e9d34b55fd9a0d0ec0288ea",
"build/prefab/lib/windows/Debug_Win32/BallisticaKitHeadlessPlus.lib": "https://files.ballistica.net/cache/ba1/da/b1/a90ccef09b8305f32520688545bf",
"build/prefab/lib/windows/Debug_Win32/BallisticaKitHeadlessPlus.pdb": "https://files.ballistica.net/cache/ba1/aa/a0/ce7ffae656e7877a72d35677114f",
"build/prefab/lib/windows/Release_Win32/BallisticaKitGenericPlus.lib": "https://files.ballistica.net/cache/ba1/26/ef/dcfa52d8f4bb9c518c51687b2b3d",
"build/prefab/lib/windows/Release_Win32/BallisticaKitGenericPlus.pdb": "https://files.ballistica.net/cache/ba1/09/e9/31c76975c552041232b3ffd5fbf0",
"build/prefab/lib/windows/Release_Win32/BallisticaKitHeadlessPlus.lib": "https://files.ballistica.net/cache/ba1/b0/35/a132ee60e1a20af514abe1276236",
"build/prefab/lib/windows/Release_Win32/BallisticaKitHeadlessPlus.pdb": "https://files.ballistica.net/cache/ba1/a4/94/64fc55a516281cc28fcfccebbd5b",
"src/assets/ba_data/python/babase/_mgen/__init__.py": "https://files.ballistica.net/cache/ba1/52/c6/c11130af7b10d6c0321add5518fa",
"src/assets/ba_data/python/babase/_mgen/enums.py": "https://files.ballistica.net/cache/ba1/38/c3/1dedd5e74f2508efc5974c8815a1",
"src/ballistica/base/mgen/pyembed/binding_base.inc": "https://files.ballistica.net/cache/ba1/ea/6a/6a4721b144e5e297b542d2a0eea2",

View File

@ -1093,8 +1093,11 @@
<w>fsets</w>
<w>fsettings</w>
<w>fsmetapackagename</w>
<w>fsmodulename</w>
<w>fsmodulepath</w>
<w>fsname</w>
<w>fspackagename</w>
<w>fspackagesroot</w>
<w>fsplit</w>
<w>fsrc</w>
<w>fstab</w>
@ -1359,6 +1362,7 @@
<w>imghdr</w>
<w>imgw</w>
<w>importlines</w>
<w>importparts</w>
<w>incentivized</w>
<w>includelines</w>
<w>includetest</w>
@ -1574,8 +1578,10 @@
<w>linenumber</w>
<w>linenums</w>
<w>linestart</w>
<w>linestripped</w>
<w>linetype</w>
<w>linetypes</w>
<w>linewords</w>
<w>linflav</w>
<w>linkstoryboards</w>
<w>linkto</w>
@ -1765,6 +1771,7 @@
<w>moduledir</w>
<w>modulefinder</w>
<w>modulename</w>
<w>modulenames</w>
<w>modulepath</w>
<w>modutils</w>
<w>moola</w>

View File

@ -1,4 +1,4 @@
### 1.7.20 (build 21090, api 8, 2023-06-10)
### 1.7.20 (build 21091, api 8, 2023-06-12)
- This seems like a good time for a `refactoring` release in anticipation of
changes coming in 1.8. Basically this means that a lot of things will be

View File

@ -649,8 +649,11 @@
<w>fsetname</w>
<w>fsets</w>
<w>fsmetapackagename</w>
<w>fsmodulename</w>
<w>fsmodulepath</w>
<w>fsname</w>
<w>fspackagename</w>
<w>fspackagesroot</w>
<w>fstestspackagename</w>
<w>fsum</w>
<w>ftos</w>
@ -799,6 +802,7 @@
<w>imagewidget</w>
<w>imayushsaini</w>
<w>importlines</w>
<w>importparts</w>
<w>incentivized</w>
<w>includelines</w>
<w>indata</w>
@ -907,6 +911,8 @@
<w>linebegin</w>
<w>linemax</w>
<w>linestart</w>
<w>linestripped</w>
<w>linewords</w>
<w>linkstoryboards</w>
<w>listobj</w>
<w>llock</w>
@ -1013,6 +1019,7 @@
<w>modetype</w>
<w>modstr</w>
<w>modtime</w>
<w>modulenames</w>
<w>moduletype</w>
<w>momemtary</w>
<w>morecnt</w>

View File

@ -7,7 +7,7 @@ from __future__ import annotations
from typing import TYPE_CHECKING
import _babase
import babase
if TYPE_CHECKING:
pass
@ -105,7 +105,7 @@ def get_all_tips() -> list[str]:
'color of sparks from its fuse: yellow..orange..red..BOOM.'
),
]
app = _babase.app
app = babase.app
if not app.iircade_mode:
tips += [
'If your framerate is choppy, try turning down resolution\nor '

View File

@ -28,7 +28,7 @@ if TYPE_CHECKING:
# Build number and version of the ballistica binary we expect to be
# using.
TARGET_BALLISTICA_BUILD = 21090
TARGET_BALLISTICA_BUILD = 21091
TARGET_BALLISTICA_VERSION = '1.7.20'
_g_env_config: EnvConfig | None = None

View File

@ -7,7 +7,8 @@ from __future__ import annotations
import weakref
from typing import Generic, TypeVar, TYPE_CHECKING
import _babase
import babase
import _bascenev1
if TYPE_CHECKING:
@ -304,7 +305,7 @@ class AssetPackage(DependencyComponent):
super().__init__()
# This is used internally by the get_package_xxx calls.
self.context = _babase.ContextRef()
self.context = babase.ContextRef()
entry = self._dep_entry()
assert entry is not None
@ -424,7 +425,7 @@ def test_depset() -> None:
# To test this, add prints on __del__ for stuff used above;
# everything should be dead at this point if we have no cycles.
print('everything should be cleaned up...')
_babase.quit()
babase.quit()
class DependencyError(Exception):

View File

@ -7,7 +7,8 @@ from __future__ import annotations
from typing import TYPE_CHECKING
import _babase
import babase
import _bascenev1
if TYPE_CHECKING:
@ -17,9 +18,9 @@ if TYPE_CHECKING:
def launch_main_menu_session() -> None:
assert _babase.app.classic is not None
assert babase.app.classic is not None
_bascenev1.new_host_session(_babase.app.classic.get_main_menu_session())
_bascenev1.new_host_session(babase.app.classic.get_main_menu_session())
def get_player_icon(sessionplayer: bascenev1.SessionPlayer) -> dict[str, Any]:
@ -45,7 +46,7 @@ def filter_chat_message(msg: str, client_id: int) -> str | None:
def local_chat_message(msg: str) -> None:
classic = _babase.app.classic
classic = babase.app.classic
assert classic is not None
party_window = (
None if classic.party_window is None else classic.party_window()

View File

@ -9,7 +9,8 @@ import weakref
from dataclasses import dataclass
from typing import TYPE_CHECKING
import _babase
import babase
import _bauiv1
if TYPE_CHECKING:
@ -199,8 +200,8 @@ def uicleanupcheck(obj: Any, widget: bauiv1.Widget) -> None:
widget.add_delete_callback(foobar)
assert _babase.app.classic is not None
_babase.app.ui_v1.cleanupchecks.append(
assert babase.app.classic is not None
babase.app.ui_v1.cleanupchecks.append(
UICleanupCheck(
obj=weakref.ref(obj), widget=widget, widget_death_time=None
)
@ -209,10 +210,10 @@ def uicleanupcheck(obj: Any, widget: bauiv1.Widget) -> None:
def ui_upkeep() -> None:
"""Run UI cleanup checks, etc. should be called periodically."""
assert _babase.app.classic is not None
ui = _babase.app.ui_v1
assert babase.app.classic is not None
ui = babase.app.ui_v1
remainingchecks = []
now = _babase.apptime()
now = babase.apptime()
for check in ui.cleanupchecks:
obj = check.obj()

View File

@ -10,7 +10,7 @@ from typing import cast
from typing import TYPE_CHECKING
import babase
from _babase import screenmessage
import _bauiv1
from bauiv1._uitypes import Window
@ -379,12 +379,12 @@ class OnScreenKeyboardWindow(Window):
self._load_keyboard()
if len(kbexports) < 2:
_bauiv1.getsound('error').play()
screenmessage(
babase.screenmessage(
babase.Lstr(resource='keyboardNoOthersAvailableText'),
color=(1, 0, 0),
)
else:
screenmessage(
babase.screenmessage(
babase.Lstr(
resource='keyboardSwitchText',
subs=[('${NAME}', self._keyboard.name)],

View File

@ -39,7 +39,7 @@ auto main(int argc, char** argv) -> int {
namespace ballistica {
// These are set automatically via script; don't modify them here.
const int kEngineBuildNumber = 21090;
const int kEngineBuildNumber = 21091;
const char* kEngineVersion = "1.7.20";
auto MonolithicMain(const core::CoreConfig& core_config) -> int {

View File

@ -35,11 +35,11 @@ class PyRequirement:
# entries; this accounts for manual installations or other nonstandard
# setups.
# Note 2: That is probably overkill. We can probably just replace
# this with a simple requirements.txt file, can't we? Feels like we're
# mostly reinventing the wheel here. We just need a clean way to
# check/list missing stuff without necessarily installing it. And as far
# as manually-installed bits, pip itself must have some way to allow for
# Note 2: That is probably overkill. We can probably just replace this
# with a simple requirements.txt file, can't we? Feels like we're mostly
# reinventing the wheel here. We just need a clean way to check/list
# missing stuff without necessarily installing it. And as far as
# manually-installed bits, pip itself must have some way to allow for
# that, right?...
PY_REQUIREMENTS = [
PyRequirement(modulename='pylint', minversion=[2, 17, 3]),
@ -63,9 +63,9 @@ PY_REQUIREMENTS = [
PyRequirement(pipname='filelock', minversion=[3, 12, 0]),
]
# Parts of full-tests suite we only run on particular days.
# (This runs in listed order so should be randomized by hand to avoid
# clustering similar tests too much)
# Parts of full-tests suite we only run on particular days. This runs in
# listed order so should be randomized by hand to avoid clustering
# similar tests too much.
SPARSE_TEST_BUILDS: list[list[str]] = [
['ios.pylibs.debug', 'android.pylibs.arm'],
['linux.package', 'android.pylibs.arm64'],
@ -82,8 +82,8 @@ SPARSE_TEST_BUILDS: list[list[str]] = [
['mac.pylibs.debug', 'android.package'],
]
# Currently only doing sparse-tests in core; not spinoffs.
# (whole word will get subbed out in spinoffs so this will be false)
# Currently only doing sparse-tests in core; not spinoffs (whole word
# will get subbed out in spinoffs so this will evaluate to False).
DO_SPARSE_TEST_BUILDS = 'ballistica' + 'kit' == 'ballisticakit'
@ -115,8 +115,9 @@ def lazybuild(target: str, category: LazyBuildCategory, command: str) -> None:
LazyBuildContext(
target=target,
command=command,
# Since this category can kick off cleans and blow things away,
# its not safe to have multiple builds going with it at once.
# Since this category can kick off cleans and blow things
# away, its not safe to have multiple builds going with it
# at once.
buildlockname=category.value,
# Regular paths; changes to these will trigger meta build.
srcpaths=[
@ -124,12 +125,14 @@ def lazybuild(target: str, category: LazyBuildCategory, command: str) -> None:
'src/meta',
'src/ballistica/shared/foundation/types.h',
],
# Our meta Makefile targets generally don't list tools scripts
# that can affect their creation as sources, so let's set up
# a catch-all here: when any of our tools stuff changes we'll
# blow away all existing meta builds.
# Update: also including featureset-defs here; any time we're
# mucking with those it's good to start fresh to be sure.
# Our meta Makefile targets generally don't list tools
# scripts that can affect their creation as sources, so
# let's set up a catch-all here: when any of our tools stuff
# changes we'll blow away all existing meta builds.
#
# Update: also including featureset-defs here; any time
# we're mucking with those it's good to start fresh to be
# sure.
srcpaths_fullclean=[
'tools/efrotools',
'tools/efrotoolsinternal',
@ -198,9 +201,9 @@ def lazybuild(target: str, category: LazyBuildCategory, command: str) -> None:
elif category is LazyBuildCategory.RESOURCES:
LazyBuildContext(
target=target,
# Even though this category currently doesn't run any
# clean commands, going to restrict to one use at a time for
# now in case we want to add that.
# Even though this category currently doesn't run any clean
# commands, going to restrict to one use at a time for now
# in case we want to add that.
buildlockname=category.value,
srcpaths=[
'Makefile',
@ -214,18 +217,18 @@ def lazybuild(target: str, category: LazyBuildCategory, command: str) -> None:
elif category is LazyBuildCategory.ASSETS:
def _filefilter(root: str, filename: str) -> bool:
# Exclude tools/spinoff; it doesn't affect asset builds
# and we don't want to break if it is a symlink pointing
# to a not-present parent repo.
# Exclude tools/spinoff; it doesn't affect asset builds and
# we don't want to break if it is a symlink pointing to a
# not-present parent repo.
if root == 'tools' and filename == 'spinoff':
return False
return True
LazyBuildContext(
target=target,
# Even though this category currently doesn't run any
# clean commands, going to restrict to one use at a time for
# now in case we want to add that.
# Even though this category currently doesn't run any clean
# commands, going to restrict to one use at a time for now
# in case we want to add that.
buildlockname=category.value,
srcpaths=[
'Makefile',
@ -240,8 +243,8 @@ def lazybuild(target: str, category: LazyBuildCategory, command: str) -> None:
elif category is LazyBuildCategory.DUMMYMODULES:
def _filefilter(root: str, filename: str) -> bool:
# In our C++ sources, only look at stuff with 'python' in the
# name.
# In our C++ sources, only look at stuff with 'python' in
# the name.
if root.startswith('ballistica'):
return 'python' in filename
@ -250,8 +253,8 @@ def lazybuild(target: str, category: LazyBuildCategory, command: str) -> None:
LazyBuildContext(
target=target,
# This category builds binaries and other crazy stuff
# so we definitely want to restrict to one at a time.
# This category builds binaries and other crazy stuff so we
# definitely want to restrict to one at a time.
buildlockname=category.value,
srcpaths=[
'config/featuresets',
@ -313,26 +316,28 @@ def gen_fulltest_buildfile_android() -> None:
"""
# pylint: disable=too-many-branches
# Its a pretty big time-suck building all architectures for
# all of our subplatforms, so lets usually just build a single one.
# We'll rotate it though and occasionally do all 4 at once just to
# be safe.
# Its a pretty big time-suck building all architectures for all of
# our subplatforms, so lets usually just build a single one. We'll
# rotate it though and occasionally do all 4 at once just to be
# safe.
dayoffset = datetime.datetime.now().timetuple().tm_yday
# Let's only do a full 'prod' once every two times through the loop.
# (it really should never catch anything that individual platforms don't)
# (it really should never catch anything that individual platforms
# don't)
modes = ['arm', 'arm64', 'x86', 'x86_64']
modes += modes
modes.append('prod')
# By default we cycle through build architectures for each flavor.
# However, for minor flavor with low risk of platform-dependent breakage
# we stick to a single one to keep disk space costs lower. (build files
# amount to several gigs per mode per flavor)
# UPDATE: Now that we have CPU time to spare, we simply always do 'arm64'
# or 'prod' depending on build type; this results in 1 or 4 architectures
# worth of build files per flavor instead of 8 (prod + 4 singles) and
# keeps our daily runs identical.
# However, for minor flavor with low risk of platform-dependent
# breakage we stick to a single one to keep disk space costs lower.
# (build files amount to several gigs per mode per flavor)
#
# UPDATE: Now that we have CPU time to spare, we simply always do
# 'arm64' or 'prod' depending on build type; this results in 1 or 4
# architectures worth of build files per flavor instead of 8 (prod +
# 4 singles) and keeps our daily runs identical.
lightweight_flavors = {'template', 'arcade', 'demo', 'iircade'}
lines = []
@ -433,10 +438,10 @@ def gen_fulltest_buildfile_windows() -> None:
lines: list[str] = []
# We want to do one regular, one headless, and one oculus build,
# but let's switch up 32 or 64 bit based on the day.
# Also occasionally throw a release build in but stick to
# mostly debug builds to keep build times speedier.
# We want to do one regular, one headless, and one oculus build, but
# let's switch up 32 or 64 bit based on the day. Also occasionally
# throw a release build in but stick to mostly debug builds to keep
# build times speedier.
pval1 = 'Win32' if dayoffset % 2 == 0 else 'x64'
pval2 = 'Win32' if (dayoffset + 1) % 2 == 0 else 'x64'
pval3 = 'Win32' if (dayoffset + 2) % 2 == 0 else 'x64'
@ -692,10 +697,11 @@ def checkenv() -> None:
)
# Make sure rsync is version 3.1.0 or newer.
# Macs come with ancient rsync versions with significant downsides such
# as single second file mod time resolution which has started to cause
# problems with build setups. So now am trying to make sure my Macs
# have an up-to-date one installed (via homebrew).
#
# Macs come with ancient rsync versions with significant downsides
# such as single second file mod time resolution which has started
# to cause problems with build setups. So now am trying to make sure
# my Macs have an up-to-date one installed (via homebrew).
rsyncver = tuple(
int(s)
for s in subprocess.run(
@ -772,8 +778,10 @@ def checkenv() -> None:
) from exc
# Check for some required python modules.
#
# FIXME: since all of these come from pip now, we should just use
# pip --list to check versions on everything instead of doing it ad-hoc.
# pip --list to check versions on everything instead of doing it
# ad-hoc.
for req in PY_REQUIREMENTS:
try:
modname = req.modulename

View File

@ -277,6 +277,7 @@ def check_python_files(self: ProjectUpdater) -> None:
from efrotools.code import get_script_filenames
scriptfiles = get_script_filenames(Path(self.projroot))
for fname in scriptfiles:
_check_python_file(self, fname)
@ -289,6 +290,7 @@ def check_python_files(self: ProjectUpdater) -> None:
'src/assets/ba_data/python',
'src/meta',
]
# EXCEPT for the following specifics.
ignores: dict[str, set[str]] = {
'tools': {
@ -337,58 +339,125 @@ def check_python_files(self: ProjectUpdater) -> None:
def _check_python_file(self: ProjectUpdater, fname: str) -> None:
# pylint: disable=too-many-branches
with open(fname, encoding='utf-8') as infile:
with open(os.path.join(self.projroot, fname), encoding='utf-8') as infile:
contents = infile.read()
lines = contents.splitlines()
# Make sure all standalone scripts are pointing to the right version
# of Python (with a few exceptions where it needs to differ)
if contents.startswith('#!/'):
copyrightline = 1
if fname not in ['tools/vmshell']:
if not contents.startswith(f'#!/usr/bin/env python{PYVER}'):
raise CleanError(
f'Incorrect shebang (first line) for ' f'{fname}.'
)
else:
copyrightline = 0
_check_python_file_shebang(self, fname, contents)
_check_python_file_license(self, fname, lines)
_check_python_file_imports(self, fname, lines)
# Special case: it there's spinoff autogenerate notice there,
# look below it.
if (
lines[copyrightline] == ''
and 'THIS FILE IS AUTOGENERATED' in lines[copyrightline + 1]
):
copyrightline += 2
if lines[copyrightline].startswith('# Synced from '):
copyrightline += 3
def _check_python_file_imports(
self: ProjectUpdater, fname: str, lines: list[str]
) -> None:
# pylint: disable=too-many-locals
# pylint: disable=too-many-branches
fspackagesroot = 'src/assets/ba_data/python/'
# Only checking modules that are part of a featureset.
if not fname.startswith(fspackagesroot):
return
parts = fname.split('/')
if parts[4].endswith('.py'):
return
fsmodulename = parts[4]
for i, line in enumerate(lines):
# FIXME: update this for the new feature-set world. Perhaps we
# can screen for imports based on feature-set dependencies or
# perhaps we should not even try and just let feature-set test
# builds catch problems like that.
if bool(False):
# Stuff under the babase module.
if '/babase/' in fname:
# Don't allow importing ba at the top level from within babase.
if line == 'import babase':
raise CleanError(
f'{fname}:{i+1}: no top level babase imports allowed'
f' under babase module.'
)
if '/bascenev1lib/' in fname:
# Don't allow importing _babase or _baplus anywhere here.
# (any internal needs should be in babase.internal)
if 'import _babase' in line:
raise CleanError(
f'{fname}:{i+1}: _babase or _baplus imports not'
f' allowed under bascenev1lib.'
)
linestripped = line.strip()
top_level = not line.startswith(' ')
linewords = linestripped.split(' ')
if len(linewords) < 2:
continue
if linewords[0] == 'import':
assert len(linewords) > 1
modulepath = linewords[1]
importparts = None
elif (
linewords[0] == 'from'
and len(linewords) > 2
and linewords[2] == 'import'
):
modulepath = linewords[1]
importparts = linewords[3:]
else:
continue
# Look for simple cases of 'from foo import bar'.
if (
importparts
and '(' not in importparts[0]
and ',' not in importparts[0]
):
single_import = importparts[0]
else:
single_import = None
modulenames = modulepath.split('.')
# These are fine.
if modulenames[0] in {'__future__', '__main__'}:
continue
# If they're importing a _foo module, make sure they are part of
# featureset foo.
if (
modulenames[0].startswith('_')
and modulenames[0] != f'_{fsmodulename}'
):
raise CleanError(
f'{fname}:{i+1}: Import of private module {modulenames[0]}'
f' not allowed from this featureset package ({fsmodulename}).'
)
# If they're importing foo._bar, make sure they are part of
# featureset foo.
for modulename in modulenames[1:]:
if modulename.startswith('_') and modulenames[0] != fsmodulename:
raise CleanError(
f'{fname}:{i+1}: import of private module {modulepath}'
f' not allowed from this featureset package'
f' ({fsmodulename}).'
)
# Modules under feature-set package foo should never be using
# the top level feature-set package foo directly; only
# individual modules under it. (foo._bar, etc). Doing this can
# lead to lots of import order problems. We currently make an
# exception for anything *not* top-level which covers
# TYPE_CHECKING blocks and functions, both of which should be
# generally ok.
if top_level and modulepath == fsmodulename:
# Also we want to allow 'from foo import bar' *IF* bar is a
# submodule. Note: currently only looking for single
# submodule imports but I don't think we ever import
# multiple.
if importparts is not None and single_import is not None:
fsmodulepath = os.path.join(
self.projroot, fspackagesroot, fsmodulename
)
assert os.path.exists(fsmodulepath)
is_submodule_import = os.path.isdir(
f'{fsmodulepath}/{single_import}'
) or os.path.isfile(f'{fsmodulepath}/{single_import}.py')
else:
is_submodule_import = False
if not is_submodule_import:
raise CleanError(
f'{fname}:{i+1}: Top level package module {modulepath}'
f' should not be imported by its own code'
' (except for within TYPE_CHECKING blocks or functions).'
' Import stuff from submodules directly.'
)
def _check_python_file_license(
self: ProjectUpdater, fname: str, lines: list[str]
) -> None:
copyrightline = _calc_python_file_copyright_line(self, lines)
# In all cases, look for our one-line legal notice.
# In the public case, look for the rest of our public license too.
if self.license_line_checks:
@ -430,6 +499,43 @@ def _check_python_file(self: ProjectUpdater, fname: str) -> None:
)
def _calc_python_file_copyright_line(
self: ProjectUpdater, lines: list[str]
) -> int:
del self # Unused.
copyrightline = 1 if lines[0].startswith('#!/') else 0
# Special case: it there's spinoff autogenerate notice there,
# look below it.
if (
lines[copyrightline] == ''
and 'THIS FILE IS AUTOGENERATED' in lines[copyrightline + 1]
):
copyrightline += 2
if lines[copyrightline].startswith('# Synced from '):
copyrightline += 3
return copyrightline
def _check_python_file_shebang(
self: ProjectUpdater, fname: str, contents: str
) -> None:
del self # Unused.
if contents.startswith('#!'):
# Make sure all standalone scripts are pointing to the right version
# of Python (with a few exceptions where it needs to differ)
if fname not in ['tools/vmshell']:
expected = f'#!/usr/bin/env python{PYVER}'
if not contents.startswith(expected):
raise CleanError(
f'Incorrect shebang (first line) for {fname}.\n'
f'Expected:\n{expected}\n\n'
f'Found:\n{contents.splitlines()[0]}'
)
def _contains_only_pycache_and_cruft(path: str) -> bool:
for _root, dirs, files in os.walk(path, topdown=True):
# Skip over hidden and pycache dirs.

View File

@ -6,8 +6,8 @@
from __future__ import annotations
import os
import subprocess
import sys
import subprocess
from pathlib import Path
from typing import TYPE_CHECKING
@ -196,8 +196,17 @@ def get_code_filenames(projroot: Path, include_generated: bool) -> list[str]:
pass
else:
codefilenames.append(path)
codefilenames.sort()
return codefilenames
out = sorted(codefilenames)
# Watch for breakage.
if not out:
print(
'WARNING: get_code_filename returning no results;'
' is something broken?',
file=sys.stderr,
)
return out
def black_base_args() -> list[str]:
@ -291,20 +300,33 @@ def get_script_filenames(projroot: Path) -> list[str]:
"""Return the Python filenames to lint-check or auto-format."""
from efrotools import getconfig
proot = f'{projroot}/'
filenames = set()
places = getconfig(projroot).get('python_source_dirs', None)
if places is None:
raise RuntimeError('python_source_dirs not declared in config')
for place in places:
for root, _dirs, files in os.walk(place):
for root, _dirs, files in os.walk(os.path.join(projroot, place)):
for fname in files:
fnamefull = os.path.join(root, fname)
# Skip symlinks (we conceivably operate on the original too)
if os.path.islink(fnamefull):
continue
if _should_include_script(fnamefull):
filenames.add(fnamefull)
return sorted(list(f for f in filenames if 'flycheck_' not in f))
assert fnamefull.startswith(proot)
filenames.add(fnamefull.removeprefix(proot))
out = sorted(list(f for f in filenames if 'flycheck_' not in f))
# Watch for breakage.
if not out:
print(
'WARNING: get_script_filename returning no results;'
' is something broken?',
file=sys.stderr,
)
return out
def runpylint(projroot: Path, filenames: list[str]) -> None: