Skip to content

Commit 05309d4

Browse files
authored
Merge pull request #146 from Distributive-Network/feature/pm-new-bug-144
A pm.new and other helpers
2 parents ae133ef + e3cc399 commit 05309d4

File tree

3 files changed

+61
-2
lines changed

3 files changed

+61
-2
lines changed

python/pythonmonkey/__init__.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
# Export public PythonMonkey APIs
22
from .pythonmonkey import *
3+
from .helpers import *
34
from .require import *
45

56
# Expose the package version
@@ -24,4 +25,4 @@
2425
Object.defineProperty(Object.prototype, "keys", keysMethod)
2526
Object.defineProperty(Array.prototype, "keys", keysMethod)
2627
}
27-
""")(lambda *args: list(args))
28+
""", { 'filename': __file__, 'fromPythonFrame': True })(lambda *args: list(args))

python/pythonmonkey/helpers.py

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
# @file helpers.py - Python->JS helpers for PythonMonkey
2+
# - typeof operator wrapper
3+
# - new operator wrapper
4+
#
5+
# @author Wes Garland, [email protected]
6+
# @date July 2023
7+
#
8+
9+
from . import pythonmonkey as pm
10+
evalOpts = { 'filename': __file__, 'fromPythonFrame': True }
11+
12+
def typeof(jsval):
13+
"""
14+
typeof function - wraps JS typeof operator
15+
"""
16+
return pm.eval("""'use strict'; (
17+
function pmTypeof(jsval)
18+
{
19+
return typeof jsval;
20+
}
21+
)""", evalOpts)(jsval);
22+
23+
def new(ctor):
24+
"""
25+
new function - emits function which wraps JS new operator, emitting a lambda which constructs a new
26+
JS object upon invocation.
27+
"""
28+
if (typeof(ctor) == 'string'):
29+
ctor = pm.eval(ctor)
30+
31+
newCtor = pm.eval("""'use strict'; (
32+
function pmNewFactory(ctor)
33+
{
34+
return function newCtor(args) {
35+
args = Array.from(args || []);
36+
return new ctor(...args);
37+
};
38+
}
39+
)""", evalOpts)(ctor)
40+
return (lambda *args: newCtor(list(args)))
41+
42+
# List which symbols are exposed to the pythonmonkey module.
43+
__all__ = [ "new", "typeof" ]
44+
45+
# Add the non-enumerable properties of globalThis which don't collide with pythonmonkey.so as exports:
46+
globalThis = pm.eval('globalThis');
47+
pmGlobals = vars(pm)
48+
49+
exports = pm.eval("""
50+
Object.getOwnPropertyNames(globalThis)
51+
.filter(prop => Object.keys(globalThis).indexOf(prop) === -1);
52+
""", evalOpts)
53+
54+
for index in range(0, int(exports.length)):
55+
name = exports[index]
56+
if (pmGlobals.get(name) == None):
57+
globals().update({name: globalThis[name]})
58+
__all__.append(name)

python/pythonmonkey/require.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -352,5 +352,5 @@ def require(moduleIdentifier: str):
352352
filename = os.path.join(os.getcwd(), "__main__") # use the CWD instead
353353
return createRequire(filename)(moduleIdentifier)
354354

355-
# Restrict what are exposed to the pythonmonkey module.
355+
# Restrict what symbols are exposed to the pythonmonkey module.
356356
__all__ = ["globalThis", "require", "createRequire", "runProgramModule"]

0 commit comments

Comments
 (0)