pytron-kit 0.3.12__py3-none-macosx_11_0_universal2.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (419) hide show
  1. pytron/__init__.py +112 -0
  2. pytron/application.py +562 -0
  3. pytron/apputils/__init__.py +0 -0
  4. pytron/apputils/chrome_ipc.py +203 -0
  5. pytron/apputils/codegen.py +261 -0
  6. pytron/apputils/config.py +303 -0
  7. pytron/apputils/deadmansswitch.py +47 -0
  8. pytron/apputils/extras.py +76 -0
  9. pytron/apputils/native.py +148 -0
  10. pytron/apputils/shell.py +73 -0
  11. pytron/apputils/windows.py +286 -0
  12. pytron/cli.py +384 -0
  13. pytron/commands/__init__.py +0 -0
  14. pytron/commands/android.py +28 -0
  15. pytron/commands/build.py +26 -0
  16. pytron/commands/doctor.py +221 -0
  17. pytron/commands/engine.py +23 -0
  18. pytron/commands/frontend.py +60 -0
  19. pytron/commands/harvest.py +112 -0
  20. pytron/commands/helpers.py +239 -0
  21. pytron/commands/info.py +50 -0
  22. pytron/commands/init.py +521 -0
  23. pytron/commands/install.py +294 -0
  24. pytron/commands/login.py +130 -0
  25. pytron/commands/package.py +228 -0
  26. pytron/commands/plugin.py +442 -0
  27. pytron/commands/run.py +312 -0
  28. pytron/commands/scan.py +210 -0
  29. pytron/commands/show.py +23 -0
  30. pytron/commands/uninstall.py +150 -0
  31. pytron/commands/utils.py +42 -0
  32. pytron/commands/workflow.py +95 -0
  33. pytron/console.py +133 -0
  34. pytron/core.py +18 -0
  35. pytron/dependencies/WebView2Loader.dll +0 -0
  36. pytron/dependencies/__init__.py +1 -0
  37. pytron/dependencies/pytron_native.so +0 -0
  38. pytron/engines/chrome/adapter.py +445 -0
  39. pytron/engines/chrome/engine.py +576 -0
  40. pytron/engines/chrome/forge.py +147 -0
  41. pytron/engines/chrome/shell/package.json +8 -0
  42. pytron/engines/chrome/shell/preload.js +12 -0
  43. pytron/engines/chrome/shell/shell.js +534 -0
  44. pytron/exceptions.py +36 -0
  45. pytron/inspector.py +201 -0
  46. pytron/inspector_ui.py +512 -0
  47. pytron/installer/Installation.nsi +236 -0
  48. pytron/installer/header.bmp +0 -0
  49. pytron/installer/pytron.ico +0 -0
  50. pytron/installer/sidebar.bmp +0 -0
  51. pytron/llms.md +98 -0
  52. pytron/manifests/README.md +29 -0
  53. pytron/manifests/windows-utf8.manifest +44 -0
  54. pytron/menu.py +128 -0
  55. pytron/nsis-setup.exe +0 -0
  56. pytron/pack/__init__.py +0 -0
  57. pytron/pack/assets.py +131 -0
  58. pytron/pack/compilers.py +289 -0
  59. pytron/pack/crystal.py +297 -0
  60. pytron/pack/graph.py +377 -0
  61. pytron/pack/inference.py +157 -0
  62. pytron/pack/installers.py +402 -0
  63. pytron/pack/introspect.py +357 -0
  64. pytron/pack/metadata.py +213 -0
  65. pytron/pack/modules.py +618 -0
  66. pytron/pack/nuitka.py +108 -0
  67. pytron/pack/pipeline.py +107 -0
  68. pytron/pack/pyinstaller.py +176 -0
  69. pytron/pack/rust_engine.py +273 -0
  70. pytron/pack/secure.py +309 -0
  71. pytron/pack/secure_loader/bin/pytron_rust_bootloader +0 -0
  72. pytron/pack/secure_loader/icon.ico +0 -0
  73. pytron/pack/utils.py +110 -0
  74. pytron/pack/virtual_root.py +124 -0
  75. pytron/platforms/__init__.py +0 -0
  76. pytron/platforms/android/__init__.py +3 -0
  77. pytron/platforms/android/android.py +103 -0
  78. pytron/platforms/android/builder.py +736 -0
  79. pytron/platforms/android/ops/build.py +79 -0
  80. pytron/platforms/android/ops/init.py +63 -0
  81. pytron/platforms/android/ops/run.py +79 -0
  82. pytron/platforms/android/ops/sync.py +770 -0
  83. pytron/platforms/android/ops/utils.py +8 -0
  84. pytron/platforms/android/shell/README.md +30 -0
  85. pytron/platforms/android/shell/app/build.gradle +64 -0
  86. pytron/platforms/android/shell/app/src/main/AndroidManifest.xml +29 -0
  87. pytron/platforms/android/shell/app/src/main/assets/python/main.py +86 -0
  88. pytron/platforms/android/shell/app/src/main/assets/python/python314.zip +0 -0
  89. pytron/platforms/android/shell/app/src/main/cpp/CMakeLists.txt +25 -0
  90. pytron/platforms/android/shell/app/src/main/cpp/include/Python.h +155 -0
  91. pytron/platforms/android/shell/app/src/main/cpp/include/abstract.h +915 -0
  92. pytron/platforms/android/shell/app/src/main/cpp/include/audit.h +30 -0
  93. pytron/platforms/android/shell/app/src/main/cpp/include/bltinmodule.h +14 -0
  94. pytron/platforms/android/shell/app/src/main/cpp/include/boolobject.h +54 -0
  95. pytron/platforms/android/shell/app/src/main/cpp/include/bytearrayobject.h +44 -0
  96. pytron/platforms/android/shell/app/src/main/cpp/include/bytesobject.h +66 -0
  97. pytron/platforms/android/shell/app/src/main/cpp/include/ceval.h +145 -0
  98. pytron/platforms/android/shell/app/src/main/cpp/include/codecs.h +176 -0
  99. pytron/platforms/android/shell/app/src/main/cpp/include/compile.h +22 -0
  100. pytron/platforms/android/shell/app/src/main/cpp/include/complexobject.h +30 -0
  101. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/abstract.h +104 -0
  102. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/audit.h +8 -0
  103. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/bytearrayobject.h +38 -0
  104. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/bytesobject.h +42 -0
  105. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/cellobject.h +50 -0
  106. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/ceval.h +43 -0
  107. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/classobject.h +71 -0
  108. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/code.h +340 -0
  109. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/compile.h +50 -0
  110. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/complexobject.h +33 -0
  111. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/context.h +107 -0
  112. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/critical_section.h +154 -0
  113. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/descrobject.h +62 -0
  114. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/dictobject.h +105 -0
  115. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/fileobject.h +16 -0
  116. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/fileutils.h +16 -0
  117. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/floatobject.h +27 -0
  118. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/frameobject.h +35 -0
  119. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/funcobject.h +185 -0
  120. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/genobject.h +56 -0
  121. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/import.h +30 -0
  122. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/initconfig.h +334 -0
  123. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/listobject.h +53 -0
  124. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/lock.h +74 -0
  125. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/longintrepr.h +184 -0
  126. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/longobject.h +89 -0
  127. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/memoryobject.h +50 -0
  128. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/methodobject.h +66 -0
  129. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/modsupport.h +26 -0
  130. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/monitoring.h +269 -0
  131. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/object.h +493 -0
  132. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/objimpl.h +104 -0
  133. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/odictobject.h +43 -0
  134. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/picklebufobject.h +31 -0
  135. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pthread_stubs.h +105 -0
  136. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pyatomic.h +614 -0
  137. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pyatomic_gcc.h +615 -0
  138. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pyatomic_msc.h +1197 -0
  139. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pyatomic_std.h +1112 -0
  140. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pyctype.h +39 -0
  141. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pydebug.h +38 -0
  142. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pyerrors.h +132 -0
  143. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pyfpe.h +15 -0
  144. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pyframe.h +45 -0
  145. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pyhash.h +54 -0
  146. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pylifecycle.h +89 -0
  147. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pymem.h +84 -0
  148. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pystate.h +275 -0
  149. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pystats.h +194 -0
  150. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pythonrun.h +96 -0
  151. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pythread.h +43 -0
  152. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/pytime.h +27 -0
  153. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/setobject.h +71 -0
  154. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/traceback.h +13 -0
  155. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/tracemalloc.h +32 -0
  156. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/tupleobject.h +40 -0
  157. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/unicodeobject.h +773 -0
  158. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/warnings.h +20 -0
  159. pytron/platforms/android/shell/app/src/main/cpp/include/cpython/weakrefobject.h +66 -0
  160. pytron/platforms/android/shell/app/src/main/cpp/include/critical_section.h +16 -0
  161. pytron/platforms/android/shell/app/src/main/cpp/include/datetime.h +267 -0
  162. pytron/platforms/android/shell/app/src/main/cpp/include/descrobject.h +100 -0
  163. pytron/platforms/android/shell/app/src/main/cpp/include/dictobject.h +108 -0
  164. pytron/platforms/android/shell/app/src/main/cpp/include/dynamic_annotations.h +499 -0
  165. pytron/platforms/android/shell/app/src/main/cpp/include/enumobject.h +17 -0
  166. pytron/platforms/android/shell/app/src/main/cpp/include/errcode.h +45 -0
  167. pytron/platforms/android/shell/app/src/main/cpp/include/exports.h +105 -0
  168. pytron/platforms/android/shell/app/src/main/cpp/include/fileobject.h +41 -0
  169. pytron/platforms/android/shell/app/src/main/cpp/include/fileutils.h +62 -0
  170. pytron/platforms/android/shell/app/src/main/cpp/include/floatobject.h +54 -0
  171. pytron/platforms/android/shell/app/src/main/cpp/include/frameobject.h +20 -0
  172. pytron/platforms/android/shell/app/src/main/cpp/include/genericaliasobject.h +14 -0
  173. pytron/platforms/android/shell/app/src/main/cpp/include/import.h +103 -0
  174. pytron/platforms/android/shell/app/src/main/cpp/include/internal/mimalloc/mimalloc/atomic.h +392 -0
  175. pytron/platforms/android/shell/app/src/main/cpp/include/internal/mimalloc/mimalloc/internal.h +969 -0
  176. pytron/platforms/android/shell/app/src/main/cpp/include/internal/mimalloc/mimalloc/prim.h +329 -0
  177. pytron/platforms/android/shell/app/src/main/cpp/include/internal/mimalloc/mimalloc/track.h +147 -0
  178. pytron/platforms/android/shell/app/src/main/cpp/include/internal/mimalloc/mimalloc/types.h +721 -0
  179. pytron/platforms/android/shell/app/src/main/cpp/include/internal/mimalloc/mimalloc.h +565 -0
  180. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_abstract.h +61 -0
  181. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_asdl.h +112 -0
  182. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_ast.h +945 -0
  183. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_ast_state.h +271 -0
  184. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_atexit.h +31 -0
  185. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_audit.h +35 -0
  186. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_backoff.h +133 -0
  187. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_bitutils.h +186 -0
  188. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_blocks_output_buffer.h +321 -0
  189. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_brc.h +73 -0
  190. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_bytes_methods.h +82 -0
  191. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_bytesobject.h +149 -0
  192. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_c_array.h +39 -0
  193. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_call.h +206 -0
  194. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_capsule.h +17 -0
  195. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_cell.h +75 -0
  196. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_ceval.h +390 -0
  197. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_ceval_state.h +48 -0
  198. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_code.h +671 -0
  199. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_codecs.h +76 -0
  200. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_compile.h +230 -0
  201. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_complexobject.h +34 -0
  202. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_condvar.h +93 -0
  203. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_context.h +59 -0
  204. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_critical_section.h +237 -0
  205. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_crossinterp.h +406 -0
  206. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_crossinterp_data_registry.h +41 -0
  207. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_debug_offsets.h +379 -0
  208. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_descrobject.h +28 -0
  209. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_dict.h +410 -0
  210. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_dict_state.h +28 -0
  211. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_dtoa.h +40 -0
  212. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_emscripten_signal.h +30 -0
  213. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_emscripten_trampoline.h +70 -0
  214. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_exceptions.h +40 -0
  215. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_faulthandler.h +100 -0
  216. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_fileutils.h +320 -0
  217. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_fileutils_windows.h +98 -0
  218. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_floatobject.h +49 -0
  219. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_flowgraph.h +47 -0
  220. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_format.h +27 -0
  221. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_frame.h +61 -0
  222. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_freelist.h +111 -0
  223. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_freelist_state.h +70 -0
  224. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_function.h +53 -0
  225. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_gc.h +378 -0
  226. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_genobject.h +43 -0
  227. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_getopt.h +22 -0
  228. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_gil.h +66 -0
  229. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_global_objects.h +34 -0
  230. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_global_objects_fini_generated.h +1592 -0
  231. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_global_strings.h +854 -0
  232. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_hamt.h +113 -0
  233. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_hashtable.h +150 -0
  234. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_import.h +141 -0
  235. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_importdl.h +139 -0
  236. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_index_pool.h +36 -0
  237. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_initconfig.h +197 -0
  238. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_instruction_sequence.h +83 -0
  239. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_instruments.h +127 -0
  240. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_interp.h +109 -0
  241. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_interp_structs.h +977 -0
  242. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_interpframe.h +401 -0
  243. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_interpframe_structs.h +95 -0
  244. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_interpolation.h +26 -0
  245. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_intrinsics.h +51 -0
  246. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_jit.h +29 -0
  247. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_list.h +81 -0
  248. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_llist.h +106 -0
  249. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_lock.h +236 -0
  250. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_long.h +319 -0
  251. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_magic_number.h +305 -0
  252. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_memoryobject.h +20 -0
  253. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_mimalloc.h +69 -0
  254. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_modsupport.h +99 -0
  255. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_moduleobject.h +62 -0
  256. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_namespace.h +21 -0
  257. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_object.h +1029 -0
  258. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_object_alloc.h +71 -0
  259. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_object_deferred.h +32 -0
  260. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_object_stack.h +95 -0
  261. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_object_state.h +49 -0
  262. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_obmalloc.h +702 -0
  263. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_obmalloc_init.h +66 -0
  264. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_opcode_metadata.h +2117 -0
  265. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_opcode_utils.h +90 -0
  266. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_optimizer.h +318 -0
  267. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_parking_lot.h +97 -0
  268. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_parser.h +78 -0
  269. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pathconfig.h +26 -0
  270. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pyarena.h +68 -0
  271. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pyatomic_ft_wrappers.h +174 -0
  272. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pybuffer.h +21 -0
  273. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pyerrors.h +213 -0
  274. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pyhash.h +91 -0
  275. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pylifecycle.h +136 -0
  276. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pymath.h +205 -0
  277. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pymem.h +145 -0
  278. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pymem_init.h +103 -0
  279. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pystate.h +339 -0
  280. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pystats.h +21 -0
  281. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pythonrun.h +68 -0
  282. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_pythread.h +172 -0
  283. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_qsbr.h +172 -0
  284. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_range.h +21 -0
  285. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_runtime.h +63 -0
  286. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_runtime_init.h +239 -0
  287. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_runtime_init_generated.h +1589 -0
  288. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_runtime_structs.h +310 -0
  289. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_semaphore.h +67 -0
  290. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_setobject.h +41 -0
  291. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_signal.h +108 -0
  292. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_sliceobject.h +20 -0
  293. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_stackref.h +791 -0
  294. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_stats.h +97 -0
  295. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_strhex.h +39 -0
  296. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_structs.h +88 -0
  297. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_structseq.h +40 -0
  298. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_symtable.h +201 -0
  299. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_sysmodule.h +32 -0
  300. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_template.h +26 -0
  301. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_time.h +334 -0
  302. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_token.h +110 -0
  303. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_traceback.h +111 -0
  304. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_tracemalloc.h +164 -0
  305. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_tstate.h +88 -0
  306. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_tuple.h +75 -0
  307. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_typedefs.h +18 -0
  308. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_typeobject.h +155 -0
  309. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_typevarobject.h +28 -0
  310. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_ucnhash.h +36 -0
  311. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_unicodeobject.h +308 -0
  312. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_unicodeobject_generated.h +3132 -0
  313. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_unionobject.h +26 -0
  314. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_uniqueid.h +57 -0
  315. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_uop_ids.h +335 -0
  316. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_uop_metadata.h +1204 -0
  317. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_warnings.h +21 -0
  318. pytron/platforms/android/shell/app/src/main/cpp/include/internal/pycore_weakref.h +133 -0
  319. pytron/platforms/android/shell/app/src/main/cpp/include/intrcheck.h +23 -0
  320. pytron/platforms/android/shell/app/src/main/cpp/include/iterobject.h +24 -0
  321. pytron/platforms/android/shell/app/src/main/cpp/include/listobject.h +55 -0
  322. pytron/platforms/android/shell/app/src/main/cpp/include/lock.h +16 -0
  323. pytron/platforms/android/shell/app/src/main/cpp/include/longobject.h +178 -0
  324. pytron/platforms/android/shell/app/src/main/cpp/include/marshal.h +31 -0
  325. pytron/platforms/android/shell/app/src/main/cpp/include/memoryobject.h +34 -0
  326. pytron/platforms/android/shell/app/src/main/cpp/include/methodobject.h +146 -0
  327. pytron/platforms/android/shell/app/src/main/cpp/include/modsupport.h +146 -0
  328. pytron/platforms/android/shell/app/src/main/cpp/include/moduleobject.h +122 -0
  329. pytron/platforms/android/shell/app/src/main/cpp/include/monitoring.h +18 -0
  330. pytron/platforms/android/shell/app/src/main/cpp/include/object.h +828 -0
  331. pytron/platforms/android/shell/app/src/main/cpp/include/objimpl.h +211 -0
  332. pytron/platforms/android/shell/app/src/main/cpp/include/opcode.h +43 -0
  333. pytron/platforms/android/shell/app/src/main/cpp/include/opcode_ids.h +259 -0
  334. pytron/platforms/android/shell/app/src/main/cpp/include/osdefs.h +57 -0
  335. pytron/platforms/android/shell/app/src/main/cpp/include/osmodule.h +17 -0
  336. pytron/platforms/android/shell/app/src/main/cpp/include/patchlevel.h +49 -0
  337. pytron/platforms/android/shell/app/src/main/cpp/include/py_curses.h +117 -0
  338. pytron/platforms/android/shell/app/src/main/cpp/include/pyatomic.h +16 -0
  339. pytron/platforms/android/shell/app/src/main/cpp/include/pybuffer.h +145 -0
  340. pytron/platforms/android/shell/app/src/main/cpp/include/pycapsule.h +58 -0
  341. pytron/platforms/android/shell/app/src/main/cpp/include/pyconfig.h +2088 -0
  342. pytron/platforms/android/shell/app/src/main/cpp/include/pydtrace.h +59 -0
  343. pytron/platforms/android/shell/app/src/main/cpp/include/pyerrors.h +335 -0
  344. pytron/platforms/android/shell/app/src/main/cpp/include/pyexpat.h +62 -0
  345. pytron/platforms/android/shell/app/src/main/cpp/include/pyframe.h +26 -0
  346. pytron/platforms/android/shell/app/src/main/cpp/include/pyhash.h +59 -0
  347. pytron/platforms/android/shell/app/src/main/cpp/include/pylifecycle.h +80 -0
  348. pytron/platforms/android/shell/app/src/main/cpp/include/pymacconfig.h +91 -0
  349. pytron/platforms/android/shell/app/src/main/cpp/include/pymacro.h +243 -0
  350. pytron/platforms/android/shell/app/src/main/cpp/include/pymath.h +65 -0
  351. pytron/platforms/android/shell/app/src/main/cpp/include/pymem.h +110 -0
  352. pytron/platforms/android/shell/app/src/main/cpp/include/pyport.h +710 -0
  353. pytron/platforms/android/shell/app/src/main/cpp/include/pystate.h +132 -0
  354. pytron/platforms/android/shell/app/src/main/cpp/include/pystats.h +28 -0
  355. pytron/platforms/android/shell/app/src/main/cpp/include/pystrcmp.h +23 -0
  356. pytron/platforms/android/shell/app/src/main/cpp/include/pystrtod.h +37 -0
  357. pytron/platforms/android/shell/app/src/main/cpp/include/pythonrun.h +42 -0
  358. pytron/platforms/android/shell/app/src/main/cpp/include/pythread.h +131 -0
  359. pytron/platforms/android/shell/app/src/main/cpp/include/pytypedefs.h +30 -0
  360. pytron/platforms/android/shell/app/src/main/cpp/include/rangeobject.h +27 -0
  361. pytron/platforms/android/shell/app/src/main/cpp/include/refcount.h +555 -0
  362. pytron/platforms/android/shell/app/src/main/cpp/include/setobject.h +49 -0
  363. pytron/platforms/android/shell/app/src/main/cpp/include/sliceobject.h +69 -0
  364. pytron/platforms/android/shell/app/src/main/cpp/include/structmember.h +56 -0
  365. pytron/platforms/android/shell/app/src/main/cpp/include/structseq.h +46 -0
  366. pytron/platforms/android/shell/app/src/main/cpp/include/sysmodule.h +27 -0
  367. pytron/platforms/android/shell/app/src/main/cpp/include/traceback.h +26 -0
  368. pytron/platforms/android/shell/app/src/main/cpp/include/tupleobject.h +46 -0
  369. pytron/platforms/android/shell/app/src/main/cpp/include/typeslots.h +96 -0
  370. pytron/platforms/android/shell/app/src/main/cpp/include/unicodeobject.h +1029 -0
  371. pytron/platforms/android/shell/app/src/main/cpp/include/warnings.h +45 -0
  372. pytron/platforms/android/shell/app/src/main/cpp/include/weakrefobject.h +46 -0
  373. pytron/platforms/android/shell/app/src/main/cpp/pytron_bridge.cpp +224 -0
  374. pytron/platforms/android/shell/app/src/main/java/com/pytron/shell/MainActivity.kt +208 -0
  375. pytron/platforms/android/shell/app/src/main/res/mipmap-xxhdpi/ic_launcher.png +0 -0
  376. pytron/platforms/android/shell/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png +0 -0
  377. pytron/platforms/android/shell/build.gradle +11 -0
  378. pytron/platforms/android/shell/gradle/wrapper/gradle-wrapper.jar +0 -0
  379. pytron/platforms/android/shell/gradle/wrapper/gradle-wrapper.properties +5 -0
  380. pytron/platforms/android/shell/gradle.properties +2 -0
  381. pytron/platforms/android/shell/gradlew.bat +85 -0
  382. pytron/platforms/android/shell/settings.gradle +16 -0
  383. pytron/platforms/darwin.py +82 -0
  384. pytron/platforms/darwin_ops/libs.py +31 -0
  385. pytron/platforms/darwin_ops/system.py +182 -0
  386. pytron/platforms/darwin_ops/utils.py +85 -0
  387. pytron/platforms/darwin_ops/webview.py +5 -0
  388. pytron/platforms/darwin_ops/window.py +102 -0
  389. pytron/platforms/interface.py +152 -0
  390. pytron/platforms/linux.py +82 -0
  391. pytron/platforms/linux_ops/libs.py +49 -0
  392. pytron/platforms/linux_ops/system.py +316 -0
  393. pytron/platforms/linux_ops/utils.py +19 -0
  394. pytron/platforms/linux_ops/webview.py +5 -0
  395. pytron/platforms/linux_ops/window.py +115 -0
  396. pytron/platforms/windows.py +136 -0
  397. pytron/platforms/windows_ops/__init__.py +0 -0
  398. pytron/platforms/windows_ops/constants.py +126 -0
  399. pytron/platforms/windows_ops/system.py +518 -0
  400. pytron/platforms/windows_ops/utils.py +3 -0
  401. pytron/platforms/windows_ops/webview.py +5 -0
  402. pytron/platforms/windows_ops/window.py +361 -0
  403. pytron/plugin.py +467 -0
  404. pytron/rcedit-x64.exe +0 -0
  405. pytron/router.py +146 -0
  406. pytron/serializer.py +240 -0
  407. pytron/shortcuts.py +279 -0
  408. pytron/state.py +76 -0
  409. pytron/tray.py +399 -0
  410. pytron/updater.py +181 -0
  411. pytron/utf8_hook.py +112 -0
  412. pytron/utils.py +44 -0
  413. pytron/webview.py +722 -0
  414. pytron_kit-0.3.12.dist-info/METADATA +131 -0
  415. pytron_kit-0.3.12.dist-info/RECORD +419 -0
  416. pytron_kit-0.3.12.dist-info/WHEEL +5 -0
  417. pytron_kit-0.3.12.dist-info/entry_points.txt +2 -0
  418. pytron_kit-0.3.12.dist-info/licenses/LICENSE +201 -0
  419. pytron_kit-0.3.12.dist-info/top_level.txt +1 -0
pytron/plugin.py ADDED
@@ -0,0 +1,467 @@
1
+ import os
2
+ import json
3
+ import sys
4
+ import importlib
5
+ import importlib.util
6
+ import logging
7
+ import subprocess
8
+ import threading
9
+ import traceback
10
+ import shutil
11
+ from typing import Dict, Any, List
12
+
13
+
14
+ class PluginError(Exception):
15
+ pass
16
+
17
+
18
+ class PluginStorage:
19
+ """Provides a plugin with its own private JSON storage and data folder."""
20
+
21
+ def __init__(self, app_instance, plugin_name):
22
+ self._app = app_instance
23
+ self._name = plugin_name
24
+ self._dir = os.path.join(self._app.storage_path, "plugins", self._name)
25
+ os.makedirs(self._dir, exist_ok=True)
26
+ self._file = os.path.join(self._dir, "data.json")
27
+
28
+ def set(self, key, value):
29
+ data = self._read()
30
+ data[key] = value
31
+ self._write(data)
32
+
33
+ def get(self, key, default=None):
34
+ data = self._read()
35
+ return data.get(key, default)
36
+
37
+ def delete(self, key):
38
+ data = self._read()
39
+ if key in data:
40
+ del data[key]
41
+ self._write(data)
42
+
43
+ def path(self, *suffixes):
44
+ """Returns an absolute path to a file in the plugin's private folder."""
45
+ path = os.path.join(self._dir, *suffixes)
46
+ os.makedirs(os.path.dirname(path), exist_ok=True)
47
+ return path
48
+
49
+ def _read(self):
50
+ if not os.path.exists(self._file):
51
+ return {}
52
+ try:
53
+ with open(self._file, "r", encoding="utf-8") as f:
54
+ return json.load(f)
55
+ except:
56
+ return {}
57
+
58
+ def _write(self, data):
59
+ with open(self._file, "w", encoding="utf-8") as f:
60
+ json.dump(data, f, indent=4)
61
+
62
+
63
+ class SupervisedApp:
64
+ """
65
+ A proxy for the App instance that protects the main app from plugin crashes.
66
+ """
67
+
68
+ def __init__(self, app, plugin_name):
69
+ self._app = app
70
+ self._plugin_name = plugin_name
71
+ self.logger = logging.getLogger(f"Pytron.Plugin.{plugin_name}.Supervisor")
72
+ self.storage = PluginStorage(app, plugin_name)
73
+
74
+ def expose(self, func, name=None, secure=False):
75
+ """Wraps the exposed function in an error handler."""
76
+ func_name = name or func.__name__
77
+
78
+ def safe_wrapper(*args, **kwargs):
79
+ try:
80
+ return func(*args, **kwargs)
81
+ except Exception as e:
82
+ self.logger.error(
83
+ f"Plugin '{self._plugin_name}' crashed in '{func_name}': {e}"
84
+ )
85
+ self.logger.debug(traceback.format_exc())
86
+ return {"error": "Plugin Execution Failed", "message": str(e)}
87
+
88
+ return self._app.expose(safe_wrapper, name=name, secure=secure)
89
+
90
+ def __getattr__(self, name):
91
+ # Delegate everything else (state, broadcast, etc.) to the real app
92
+ return getattr(self._app, name)
93
+
94
+
95
+ class Plugin:
96
+ """
97
+ Represents a loaded Pytron Plugin.
98
+ """
99
+
100
+ def __init__(self, manifest_path: str):
101
+ self.manifest_path = os.path.abspath(manifest_path)
102
+ self.directory = os.path.dirname(self.manifest_path)
103
+ self.manifest = self._load_manifest()
104
+ self.logger = logging.getLogger(f"Pytron.Plugin.{self.name}")
105
+
106
+ def _load_manifest(self) -> Dict[str, Any]:
107
+ if not os.path.exists(self.manifest_path):
108
+ raise PluginError(f"Manifest not found at {self.manifest_path}")
109
+
110
+ try:
111
+ with open(self.manifest_path, "r") as f:
112
+ data = json.load(f)
113
+ except json.JSONDecodeError as e:
114
+ raise PluginError(f"Invalid JSON in manifest: {e}")
115
+
116
+ required_fields = ["name", "version", "entry_point"]
117
+ for field in required_fields:
118
+ if field not in data:
119
+ raise PluginError(f"Manifest missing required field: {field}")
120
+
121
+ return data
122
+
123
+ @property
124
+ def name(self) -> str:
125
+ return self.manifest.get("name", "unknown")
126
+
127
+ @property
128
+ def version(self) -> str:
129
+ return self.manifest.get("version", "0.0.0")
130
+
131
+ @property
132
+ def python_dependencies(self) -> List[str]:
133
+ return self.manifest.get("python_dependencies", [])
134
+
135
+ @property
136
+ def npm_dependencies(self) -> Dict[str, str]:
137
+ return self.manifest.get("npm_dependencies", {})
138
+
139
+ @property
140
+ def entry_point(self) -> str:
141
+ return self.manifest.get("entry_point")
142
+
143
+ @property
144
+ def ui_entry(self) -> str:
145
+ """Relative path to the JS/WebComponent entry point for this plugin."""
146
+ return self.manifest.get("ui_entry")
147
+
148
+ @property
149
+ def config(self) -> Dict[str, Any]:
150
+ """Plugin-specific configuration from manifest."""
151
+ return self.manifest.get("config", {})
152
+
153
+ @property
154
+ def isolated(self) -> bool:
155
+ """Whether this plugin should run in its own process/venv."""
156
+ return self.manifest.get("isolated", False)
157
+
158
+ def check_js_dependencies(self) -> bool:
159
+ """
160
+ Checks if JS dependencies are installed (rudimentary check for node_modules).
161
+ """
162
+ if not self.npm_dependencies:
163
+ return True
164
+ node_modules = os.path.join(self.directory, "node_modules")
165
+ return os.path.exists(node_modules) and os.path.isdir(node_modules)
166
+
167
+ def check_dependencies(self) -> bool:
168
+ """
169
+ Checks if Python dependencies are installed.
170
+ Returns True if all dependencies are present.
171
+ """
172
+ missing = []
173
+ for dep in self.python_dependencies:
174
+ try:
175
+ importlib.import_module(dep) # nosemgrep
176
+ except ImportError:
177
+ missing.append(dep)
178
+
179
+ if missing:
180
+ self.logger.warning(f"Missing Python dependencies: {', '.join(missing)}")
181
+ return False
182
+
183
+ return True
184
+
185
+ def install_dependencies(self, frontend_dir: str = None, provider: str = "npm"):
186
+ """
187
+ Attempts to install missing Python and JS dependencies.
188
+ """
189
+ # GUARD: Do not install dependencies in packaged/frozen apps.
190
+ if getattr(sys, "frozen", False):
191
+ self.logger.info(
192
+ f"Skipping dependency install for '{self.name}' (Frozen Environment)"
193
+ )
194
+ return
195
+
196
+ # 1. Python Dependencies
197
+ py_deps = self.python_dependencies
198
+ if py_deps:
199
+ # Check if they are already installed to avoid redundant operations
200
+ if self.check_dependencies():
201
+ self.logger.debug(f"Python dependencies for {self.name} are satisfied.")
202
+ else:
203
+ self.logger.info(
204
+ f"Installing Python dependencies for {self.name}: {py_deps}"
205
+ )
206
+ try:
207
+ # Resolve the project's virtual environment if it exists
208
+ python_exe = sys.executable
209
+ venv_scripts = os.path.join(os.getcwd(), "env", "Scripts", "python.exe")
210
+ venv_bin = os.path.join(os.getcwd(), "env", "bin", "python")
211
+
212
+ if os.path.exists(venv_scripts):
213
+ python_exe = venv_scripts
214
+ elif os.path.exists(venv_bin):
215
+ python_exe = venv_bin
216
+
217
+ subprocess.check_call([python_exe, "-m", "pip", "install"] + py_deps)
218
+ self.logger.info(f"Python dependencies installed into {python_exe}")
219
+ except subprocess.CalledProcessError as e:
220
+ self.logger.error(f"Failed to install Python dependencies: {e}")
221
+ raise PluginError(f"Python dependency installation failed: {e}")
222
+
223
+ # 2. JS Dependencies
224
+ js_deps = self.npm_dependencies
225
+ if js_deps:
226
+ if self.check_js_dependencies():
227
+ self.logger.debug(f"JS dependencies for {self.name} are satisfied.")
228
+ return
229
+
230
+ # ISOLATION: Install inside the plugin directory
231
+ target_dir = self.directory
232
+
233
+ self.logger.info(
234
+ f"Installing JS dependencies for {self.name} using '{provider}' in {target_dir} for isolation..."
235
+ )
236
+
237
+ # Ensure a package.json exists in the plugin directory
238
+ pkg_json_path = os.path.join(target_dir, "package.json")
239
+ if not os.path.exists(pkg_json_path):
240
+ pkg_data = {
241
+ "name": f"pytron-plugin-{self.name}",
242
+ "version": self.version,
243
+ "dependencies": js_deps,
244
+ }
245
+ with open(pkg_json_path, "w") as f:
246
+ json.dump(pkg_data, f, indent=2)
247
+
248
+ try:
249
+ # Find JS provider binary
250
+ provider_bin = shutil.which(provider)
251
+ if not provider_bin:
252
+ self.logger.warning(
253
+ f"JS Provider '{provider}' not found in PATH. Skipping JS dependencies."
254
+ )
255
+ return
256
+
257
+ subprocess.check_call(
258
+ [provider_bin, "install"],
259
+ cwd=target_dir,
260
+ shell=False,
261
+ ) # nosec B603
262
+ self.logger.info(
263
+ f"JS dependencies installed successfully using {provider}."
264
+ )
265
+ except Exception as e:
266
+ self.logger.error(f"Failed to install JS dependencies: {e}")
267
+ raise PluginError(f"JS dependency installation failed: {e}")
268
+ # We don't necessarily want to crash the whole app if NPM is missing,
269
+ # but we should log it.
270
+
271
+ def load(self, app_instance):
272
+ """
273
+ Loads the entry point and runs initialization. (Senior Fix: Isolated Namespace)
274
+ """
275
+ # Ensure we use an absolute path
276
+ plugin_dir = os.path.abspath(self.directory)
277
+ entry_str = self.entry_point
278
+
279
+ if ":" not in entry_str:
280
+ raise PluginError(
281
+ f"Invalid entry_point format '{entry_str}'. Expected 'module:function' or 'module:Class'"
282
+ )
283
+
284
+ module_name, object_name = entry_str.split(":")
285
+
286
+ # Senior Fix: Define a unique name for the module (e.g., "pytron_plugins.myplugin")
287
+ # This prevents collisions if multiple plugins have a 'main.py' or 'app.py'
288
+ safe_name = self.name.replace("-", "_").replace(".", "_")
289
+ unique_module_name = f"pytron_plugins.{safe_name}"
290
+
291
+ # Resolve the file path (handles packages and submodules)
292
+ module_path_parts = module_name.split(".")
293
+ file_path = os.path.join(plugin_dir, *module_path_parts) + ".py"
294
+ if not os.path.exists(file_path):
295
+ init_path = os.path.join(plugin_dir, *module_path_parts, "__init__.py")
296
+ if os.path.exists(init_path):
297
+ file_path = init_path
298
+
299
+ if not os.path.exists(file_path):
300
+ raise PluginError(
301
+ f"Could not find entry point file for plugin '{self.name}': {file_path}"
302
+ )
303
+
304
+ # Create the Supervised proxy
305
+ supervised_app = SupervisedApp(app_instance, self.name)
306
+
307
+ try:
308
+ # Senior Fix: Load the module directly via spec without polluting global sys.path
309
+ spec = importlib.util.spec_from_file_location(unique_module_name, file_path)
310
+ if spec and spec.loader:
311
+ self.module = importlib.util.module_from_spec(spec)
312
+ sys.modules[unique_module_name] = self.module # Register it safely
313
+
314
+ # To support local imports inside the plugin folder, we briefly add to path
315
+ # only during the execution of the module.
316
+ path_added = False
317
+ if plugin_dir not in sys.path:
318
+ sys.path.insert(0, plugin_dir)
319
+ path_added = True
320
+
321
+ try:
322
+ spec.loader.exec_module(self.module)
323
+ except ImportError as e:
324
+ raise PluginError(f"Import Error in {self.name}: {e}")
325
+ finally:
326
+ if path_added and plugin_dir in sys.path:
327
+ sys.path.remove(plugin_dir)
328
+ else:
329
+ raise PluginError(f"Could not load module spec for {self.name}")
330
+
331
+ # Get the object
332
+ if not hasattr(self.module, object_name):
333
+ raise PluginError(
334
+ f"Entry point '{object_name}' not found in module '{module_name}'"
335
+ )
336
+
337
+ entry_obj = getattr(self.module, object_name)
338
+
339
+ def init_plugin():
340
+ try:
341
+ self.logger.debug(
342
+ f"Initializing entry point: {entry_obj} (Type: {type(entry_obj).__name__})"
343
+ )
344
+
345
+ # 1. If it's a function, call it with `supervised_app`
346
+ if callable(entry_obj) and not isinstance(entry_obj, type):
347
+ self.logger.info(
348
+ f"Initializing plugin '{self.name}' via function '{object_name}'"
349
+ )
350
+ # Check for manual configuration from the 'plugins' pseudo-module if it exists
351
+ manual_config = {}
352
+ if "plugins" in sys.modules:
353
+ p_mod = sys.modules["plugins"]
354
+ if hasattr(p_mod, "get_registered_config"):
355
+ manual_config = p_mod.get_registered_config(self.name)
356
+
357
+ if manual_config:
358
+ self.logger.info(
359
+ f"Applying manual configuration to '{self.name}': {list(manual_config.keys())}"
360
+ )
361
+
362
+ self.instance = entry_obj(supervised_app, **manual_config)
363
+
364
+ # 2. If it's a class, instantiate it with `supervised_app`
365
+ elif isinstance(entry_obj, type):
366
+ self.logger.info(
367
+ f"Initializing plugin '{self.name}' via class '{object_name}'"
368
+ )
369
+ # Check for manual configuration from the 'plugins' pseudo-module if it exists
370
+ manual_config = {}
371
+ if "plugins" in sys.modules:
372
+ p_mod = sys.modules["plugins"]
373
+ if hasattr(p_mod, "get_registered_config"):
374
+ manual_config = p_mod.get_registered_config(self.name)
375
+
376
+ if manual_config:
377
+ self.logger.info(
378
+ f"Applying manual configuration to '{self.name}': {list(manual_config.keys())}"
379
+ )
380
+
381
+ self.instance = entry_obj(supervised_app, **manual_config)
382
+
383
+ # If the class has a 'setup' method, call it
384
+ if hasattr(self.instance, "setup"):
385
+ self.instance.setup()
386
+
387
+ else:
388
+ self.logger.error(
389
+ f"Entry point '{object_name}' is not callable. Got type: {type(entry_obj)}"
390
+ )
391
+
392
+ except TypeError as e:
393
+ if "NoneType" in str(e) and "callable" in str(e):
394
+ self.logger.error(
395
+ f"CRITICAL: 'NoneType' object is not callable in {self.name}. Check if entry point is valid or if dependencies are missing."
396
+ )
397
+ self.logger.error(
398
+ f"Plugin '{self.name}' initialization crash (TypeError): {e}"
399
+ )
400
+ self.logger.debug(traceback.format_exc())
401
+ except Exception as e:
402
+ self.logger.error(f"Plugin '{self.name}' initialization crash: {e}")
403
+ self.logger.debug(traceback.format_exc())
404
+
405
+ if self.isolated:
406
+ self.logger.info(
407
+ f"Plugin '{self.name}' is isolated. Starting in worker thread..."
408
+ )
409
+ thread = threading.Thread(
410
+ target=init_plugin, name=f"Plugin-{self.name}", daemon=True
411
+ )
412
+ thread.start()
413
+ else:
414
+ init_plugin()
415
+
416
+ except Exception as e:
417
+ raise PluginError(f"Failed to load plugin '{self.name}': {e}")
418
+
419
+ def unload(self):
420
+ """
421
+ Unloads the plugin by calling its teardown method if available.
422
+ """
423
+ if hasattr(self, "instance") and self.instance:
424
+ if hasattr(self.instance, "teardown"):
425
+ try:
426
+ self.instance.teardown()
427
+ self.logger.info(f"Plugin '{self.name}' torn down successfully.")
428
+ except Exception as e:
429
+ self.logger.error(f"Error tearing down plugin '{self.name}': {e}")
430
+ self.instance = None
431
+
432
+ if hasattr(self, "module") and self.module:
433
+ # Note: We don't remove from sys.modules to avoid breaking background threads
434
+ # that might still be using the code, but we clear the local reference.
435
+ del self.module
436
+
437
+ def invoke_package_hook(self, context: Dict[str, Any]):
438
+ """
439
+ Invoked during 'pytron package'. Allows plugins to add extra data,
440
+ hidden imports, or run custom build scripts.
441
+ """
442
+ if hasattr(self, "instance") and hasattr(self.instance, "on_package"):
443
+ try:
444
+ self.logger.info(f"Invoking on_package hook for '{self.name}'...")
445
+ self.instance.on_package(context)
446
+ except Exception as e:
447
+ self.logger.error(f"Error in on_package hook for '{self.name}': {e}")
448
+ self.logger.debug(traceback.format_exc())
449
+
450
+
451
+ def discover_plugins(plugins_dir: str) -> List[Plugin]:
452
+ """
453
+ Utility to find all plugins in a directory without loading them.
454
+ """
455
+ plugins = []
456
+ if not os.path.exists(plugins_dir):
457
+ return plugins
458
+
459
+ for item in os.listdir(plugins_dir):
460
+ plugin_path = os.path.join(plugins_dir, item)
461
+ manifest_path = os.path.join(plugin_path, "manifest.json")
462
+ if os.path.isdir(plugin_path) and os.path.exists(manifest_path):
463
+ try:
464
+ plugins.append(Plugin(manifest_path))
465
+ except Exception:
466
+ pass
467
+ return plugins
pytron/rcedit-x64.exe ADDED
Binary file
pytron/router.py ADDED
@@ -0,0 +1,146 @@
1
+ import re
2
+ import urllib.parse
3
+ import inspect
4
+ import logging
5
+
6
+
7
+ class DeepLink:
8
+ """
9
+ Represents a parsed Deep Link.
10
+ """
11
+
12
+ def __init__(self, raw_url: str, params: dict = None):
13
+ self.raw_url = raw_url
14
+ self.parsed = urllib.parse.urlparse(raw_url)
15
+ self.scheme = self.parsed.scheme
16
+ self.netloc = self.parsed.netloc
17
+ self.path = self.parsed.path
18
+
19
+ # Parse query params (returns dict of lists)
20
+ self.query = urllib.parse.parse_qs(self.parsed.query)
21
+
22
+ # Flatten query params if single value (optional utility)
23
+ self.args = {k: v[0] if len(v) == 1 else v for k, v in self.query.items()}
24
+
25
+ # Path parameters extracted from route
26
+ self.params = params or {}
27
+
28
+ def __repr__(self):
29
+ return f"<DeepLink scheme='{self.scheme}' path='{self.netloc}{self.path}' params={self.params} args={self.args}>"
30
+
31
+
32
+ class Router:
33
+ """
34
+ Handles matching Deep Links to registered callback functions.
35
+ """
36
+
37
+ def __init__(self, logger=None):
38
+ self.routes = []
39
+ self._default_handler = None
40
+ self.logger = logger or logging.getLogger("Pytron.Router")
41
+
42
+ def add_route(self, pattern: str, func):
43
+ """
44
+ Registers a route pattern.
45
+ Pattern examples:
46
+ - "home" matches myapp://home
47
+ - "document/{id}" matches myapp://document/123
48
+ - "user/{name}/profile" matches myapp://user/alice/profile
49
+ """
50
+ # 1. Normalize pattern to ensure it handles the 'netloc' vs 'path' ambiguity of custom schemes
51
+ # We treat everything after 'scheme://' as the routable path.
52
+ clean_pattern = pattern.strip("/")
53
+
54
+ # 2. Convert {param} to Regex Group (?P<param>[^/]+)
55
+ # Escape special regex chars but leave our braces
56
+ regex_pattern = re.escape(clean_pattern)
57
+
58
+ # Replace escaped braces \{param\} back to capture groups
59
+ # We manually build the regex: replace \{([^}]+)\} with (?P<\1>[^/]+)
60
+ # Note: re.escape escapes {, }, so we look for \\{ and \\}
61
+ regex_pattern = re.sub(
62
+ r"\\{([a-zA-Z0-9_]+)\\}", r"(?P<\1>[^/]+)", regex_pattern
63
+ )
64
+
65
+ # Anchor start/end
66
+ regex_pattern = f"^{regex_pattern}$"
67
+
68
+ self.routes.append(
69
+ {"pattern": clean_pattern, "regex": re.compile(regex_pattern), "func": func}
70
+ )
71
+ self.logger.debug(f"Registered deep link route: {clean_pattern}")
72
+
73
+ def route(self, pattern: str):
74
+ """
75
+ Decorator to register a route.
76
+ """
77
+
78
+ def decorator(func):
79
+ self.add_route(pattern, func)
80
+ return func
81
+
82
+ return decorator
83
+
84
+ def set_default_handler(self, func):
85
+ self._default_handler = func
86
+
87
+ def dispatch(self, raw_url: str):
88
+ """
89
+ Parses the URL and calls the matching handler.
90
+ """
91
+ if not raw_url:
92
+ return
93
+
94
+ try:
95
+ parsed = urllib.parse.urlparse(raw_url)
96
+ # Reconstruct the "routable path": netloc + path
97
+ # e.g. myapp://user/1 -> netloc="user", path="/1" -> "user/1"
98
+ # e.g. myapp://home -> netloc="home", path="" -> "home"
99
+ routable_path = f"{parsed.netloc}{parsed.path}".strip("/")
100
+
101
+ matched = False
102
+ for route in self.routes:
103
+ match = route["regex"].match(routable_path)
104
+ if match:
105
+ params = match.groupdict()
106
+ link = DeepLink(raw_url, params)
107
+ self._invoke_handler(route["func"], link)
108
+ matched = True
109
+ break
110
+
111
+ if not matched:
112
+ self.logger.debug(f"No route matched for: {routable_path}")
113
+ if self._default_handler:
114
+ link = DeepLink(raw_url)
115
+ self._invoke_handler(self._default_handler, link)
116
+
117
+ except Exception as e:
118
+ self.logger.error(f"Error dispatching deep link '{raw_url}': {e}")
119
+
120
+ def _invoke_handler(self, func, link):
121
+ """
122
+ Invokes the handler, injecting arguments if needed.
123
+ """
124
+ try:
125
+ sig = inspect.signature(func)
126
+ kwargs = {}
127
+
128
+ # 1. Check if handler wants the full 'link' object
129
+ if "link" in sig.parameters:
130
+ kwargs["link"] = link
131
+
132
+ # 2. Inject path params if they match argument names
133
+ for name, value in link.params.items():
134
+ if name in sig.parameters:
135
+ kwargs[name] = value
136
+
137
+ # 3. Inject query args if they match argument names
138
+ for name, value in link.args.items():
139
+ if name in sig.parameters:
140
+ kwargs[name] = value
141
+
142
+ # Invoke
143
+ func(**kwargs)
144
+
145
+ except Exception as e:
146
+ self.logger.error(f"Handler failed for deep link: {e}")