init commit
This commit is contained in:
@@ -0,0 +1,215 @@
|
||||
import inspect
|
||||
from typing import Callable
|
||||
|
||||
|
||||
class RegisteredActionsAccessor:
|
||||
def __init__(self, registered_actions, namespace):
|
||||
self.registered_actions = registered_actions
|
||||
self.namespace = namespace
|
||||
|
||||
def __getattr__(self, name):
|
||||
for category in ("test", "module"):
|
||||
cat_actions = self.registered_actions[category]
|
||||
if self.namespace in cat_actions:
|
||||
if name in cat_actions[self.namespace]:
|
||||
return cat_actions[self.namespace][name]
|
||||
|
||||
raise AttributeError(f"Couldn't find action {self.namespace}.{name}")
|
||||
|
||||
def __call__(self, *args, **kwargs):
|
||||
# Provide a useful error message if people try something like
|
||||
# actions.my_action() when they should do actions.user.my_action()
|
||||
raise RuntimeError(f"actions.{self.namespace}() is not an available action")
|
||||
|
||||
|
||||
class Actions:
|
||||
"""
|
||||
Implements something like talon.actions. You can use the register
|
||||
function to add in an action definition from your test (e.g. a mock).
|
||||
"""
|
||||
|
||||
def __init__(self):
|
||||
self.registered_actions = {
|
||||
"module": {},
|
||||
"test": {},
|
||||
}
|
||||
|
||||
# Some built in actions
|
||||
self.register_module_action("", "key", lambda x: None)
|
||||
self.register_module_action("", "insert", lambda x: None)
|
||||
self.register_module_action("", "sleep", lambda x: None)
|
||||
self.register_module_action("edit", "selected_text", lambda: "test")
|
||||
|
||||
def reset_test_actions(self):
|
||||
self.registered_actions["test"] = {}
|
||||
|
||||
def register_module_action(self, namespace: str, name: str, func: Callable):
|
||||
"""
|
||||
Registers an action to the module category. This should
|
||||
only be called by importing files containing module definitions.
|
||||
It won't be reset between test runs (or test files). Use
|
||||
register_test_action and reset_test_actions to temporarily override
|
||||
actions.
|
||||
"""
|
||||
|
||||
self._register_action("module", namespace, name, func)
|
||||
|
||||
def register_test_action(self, namespace: str, name: str, func: Callable):
|
||||
"""
|
||||
Registers the given action, use like:
|
||||
|
||||
actions.register("user.my_action", lambda: None)
|
||||
"""
|
||||
|
||||
self._register_action("test", namespace, name, func)
|
||||
|
||||
def _register_action(
|
||||
self, category: str, namespace: str, name: str, func: Callable
|
||||
):
|
||||
if namespace not in self.registered_actions[category]:
|
||||
self.registered_actions[category][namespace] = {}
|
||||
|
||||
self.registered_actions[category][namespace][name] = func
|
||||
|
||||
def __getattr__(self, name):
|
||||
try:
|
||||
# If name exists as a direct property of this class, then
|
||||
# use that
|
||||
return object.__getattribute__(self, name)
|
||||
except AttributeError:
|
||||
pass
|
||||
|
||||
try:
|
||||
# Else if name is an action like actions.key
|
||||
# that has no namespace then return that.
|
||||
default_accessor = RegisteredActionsAccessor(self.registered_actions, "")
|
||||
return getattr(default_accessor, name)
|
||||
except AttributeError:
|
||||
# Otherwise treat name as an action namespace
|
||||
# (like actions.user).
|
||||
return RegisteredActionsAccessor(self.registered_actions, name)
|
||||
|
||||
|
||||
class Module:
|
||||
"""
|
||||
Implements something like the Module class built in to Talon
|
||||
"""
|
||||
|
||||
def list(self, *args, **kwargs):
|
||||
pass
|
||||
|
||||
def setting(self, *args, **kwargs):
|
||||
pass
|
||||
|
||||
def capture(self, rule=None):
|
||||
def __funcwrapper(func):
|
||||
def __inner(*args, **kwargs):
|
||||
return func(*args, **kwargs)
|
||||
|
||||
return __inner
|
||||
|
||||
return __funcwrapper
|
||||
|
||||
def tag(self, name, desc=None):
|
||||
pass
|
||||
|
||||
def action_class(self, target_class):
|
||||
# Register all the methods on the class with our actions implementation
|
||||
for name, func in inspect.getmembers(target_class, inspect.isfunction):
|
||||
actions.register_module_action("user", name, func)
|
||||
|
||||
return target_class
|
||||
|
||||
|
||||
class Context:
|
||||
"""
|
||||
Implements something like the Context class built in to Talon
|
||||
"""
|
||||
|
||||
lists = {}
|
||||
|
||||
def action_class(self, path=None):
|
||||
def __funcwrapper(clazz):
|
||||
return clazz
|
||||
|
||||
return __funcwrapper
|
||||
|
||||
def capture(self, name: str, rule: str = None):
|
||||
def __funcwrapper(func):
|
||||
def __inner(*args, **kwargs):
|
||||
return func(*args, **kwargs)
|
||||
|
||||
return __inner
|
||||
|
||||
return __funcwrapper
|
||||
|
||||
|
||||
class ImgUI:
|
||||
"""
|
||||
Stub out ImgUI so we don't get crashes
|
||||
"""
|
||||
|
||||
GUI = None
|
||||
|
||||
def open(self):
|
||||
def __funcwrapper(func):
|
||||
def __inner(*args, **kwargs):
|
||||
return func(*args, **kwargs)
|
||||
|
||||
return __inner
|
||||
|
||||
return __funcwrapper
|
||||
|
||||
|
||||
class UI:
|
||||
"""
|
||||
Stub out UI so we don't get crashes
|
||||
"""
|
||||
|
||||
def register(*args, **kwargs):
|
||||
pass
|
||||
|
||||
|
||||
class Settings:
|
||||
"""
|
||||
Implements something like talon.settings
|
||||
"""
|
||||
|
||||
|
||||
class Registry:
|
||||
"""
|
||||
Implements something like Talon's registry
|
||||
"""
|
||||
|
||||
|
||||
class Resource:
|
||||
"""
|
||||
Implements something like the talon resource system
|
||||
"""
|
||||
|
||||
def open(self, path: str, mode: str = "r"):
|
||||
return open(path, mode, encoding="utf-8")
|
||||
|
||||
def watch(self, path: str):
|
||||
return lambda f: f
|
||||
|
||||
|
||||
class App:
|
||||
"""
|
||||
Implements something like the talon app variable
|
||||
"""
|
||||
|
||||
platform = "mac"
|
||||
|
||||
|
||||
actions = Actions()
|
||||
app = App
|
||||
clip = None
|
||||
imgui = ImgUI()
|
||||
ui = UI()
|
||||
settings = Settings()
|
||||
resource = Resource()
|
||||
registry = Registry()
|
||||
|
||||
# Indicate to test files that they should load since we're running in test mode
|
||||
test_mode = True
|
||||
@@ -0,0 +1,7 @@
|
||||
TextArea = None
|
||||
|
||||
Span = None
|
||||
|
||||
DarkThemeLabels = None
|
||||
|
||||
LightThemeLabels = None
|
||||
@@ -0,0 +1,11 @@
|
||||
# This is a class in the Talon runtime, but is only used as a type in `community`. We
|
||||
# stub it here as a blank class, since there are (for example) functions which
|
||||
# check isinstance(some_input, Phrase), and for testing we want these tests to
|
||||
# return False.
|
||||
class Phrase:
|
||||
pass
|
||||
|
||||
|
||||
# grammar.vm.Phrase is also used sometimes.
|
||||
class vm:
|
||||
Phrase = Phrase
|
||||
Reference in New Issue
Block a user