Skip to content
This repository was archived by the owner on Oct 15, 2025. It is now read-only.

Commit 6189639

Browse files
author
Hörmet Yiltiz
committed
Initial draft for lisp eval support
1 parent 50a2d4e commit 6189639

1 file changed

Lines changed: 106 additions & 0 deletions

File tree

lisp_eval/__init__.py

Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
# -*- coding: utf-8 -*-
2+
# Copyright (c) 2025 Hormet Yiltiz
3+
4+
from builtins import pow
5+
from pathlib import Path
6+
import subprocess
7+
8+
from albert import *
9+
10+
md_iid = '2.3'
11+
md_version = "1.6"
12+
md_name = "S-Exp Eval"
13+
md_description = "Evaluate S-Expression via Fennel or Emacs"
14+
md_license = "BSD-3"
15+
md_url = "https://github.com/albertlauncher/python/tree/main/fennel_eval"
16+
md_authors = "@manuelschneid3r"
17+
18+
class Plugin(PluginInstance, TriggerQueryHandler):
19+
20+
def __init__(self):
21+
# search for a language supporting S-Exp: fennel, janet, elisp, clojure, racket
22+
# TODO: this should be a configurable option
23+
# Users should make available the executables in the system PATH
24+
lang_opts = {
25+
'janet': {
26+
'prog': 'janet',
27+
'args': ['-e', '(print {})'],
28+
'url': 'https://janet-lang.org/assets/janet-big.png'
29+
},
30+
'fennel': {
31+
'prog': 'fennel',
32+
'args': ['-e', '(print {})'],
33+
'url': 'https://janet-lang.org/assets/janet-big.png'
34+
},
35+
'elisp': {
36+
'prog': 'emacs',
37+
'args': ['--batch', '--eval', '(print {})'],
38+
'url': 'https://www.gnu.org/software/emacs/images/emacs.png'
39+
},
40+
'racket': {
41+
'prog': 'racket',
42+
'args': ['-e', '(print {})'],
43+
'url': 'https://racket-lang.org/img/racket-logo.svg'
44+
},
45+
}
46+
self.lang_opts = lang_opts
47+
48+
test_sexp = '(+ 1 1)'
49+
detected_langs = []
50+
for lang, args in lang_opts.items():
51+
script = args['args'][-1].format(test_sexp)
52+
try:
53+
proc = subprocess.run([args['prog'], *args['args'][0:-1], script], input=script.encode(),
54+
stdout=subprocess.PIPE)
55+
result = proc.stdout.strip()
56+
if result:
57+
detected_langs.append(lang)
58+
except FileNotFoundError as ex:
59+
# TODO: does Albert has a logger?
60+
continue
61+
62+
63+
PluginInstance.__init__(self)
64+
TriggerQueryHandler.__init__(
65+
self, self.id, self.name, self.description,
66+
synopsis='<Evaluate Lisp S-Expression>',
67+
defaultTrigger='() '
68+
)
69+
self.detected_langs = detected_langs
70+
self.call_external = lang_opts[detected_langs[0]]
71+
self.iconUrls = self.call_external['url']
72+
73+
def handleTriggerQuery(self, query):
74+
act = lambda script: (
75+
lambda: runDetachedProcess([
76+
self.call_external['prog'],
77+
*self.call_external['args'][0:-1],
78+
self.call_external['args'][-1].format(script)]
79+
)
80+
)
81+
82+
stripped = query.string.strip()
83+
if stripped:
84+
try:
85+
result = act(stripped)
86+
87+
except Exception as ex:
88+
result = ex
89+
90+
result_str = str(result)
91+
92+
query.add(StandardItem(
93+
id=self.id,
94+
text=result_str,
95+
subtext=type(result).__name__,
96+
inputActionText=query.trigger + result_str,
97+
iconUrls=self.iconUrls,
98+
actions = [
99+
Action("copy", "Copy result to clipboard", lambda r=result_str: setClipboardText(r)),
100+
Action("exec", "Evaluate S-Expression", lambda r=result_str: act(r)),
101+
]
102+
))
103+
104+
# if __name__ == '__main__':
105+
# plugin = Plugin()
106+
# plugin.run()

0 commit comments

Comments
 (0)