aboutsummaryrefslogtreecommitdiff
path: root/piston.py
blob: 3b8504d9a5f474182177c102697e701a0cd7493d (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
#
# Piston commands
#
# Copyright © 2023 by luk3yx
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Affero General Public License as
# published by the Free Software Foundation, either version 3 of the
# License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public License
# along with this program.  If not, see <https://www.gnu.org/licenses/>.
#

import requests

PISTON_URL = 'https://emkc.org/api/v2/piston/execute'


@register_command('sh', 'bash')
def sh(irc, hostmask, is_admin, args):
    res = requests.post(PISTON_URL, json={
        'language': 'bash',
        'version': '*',
        'files': [{'name': 'main.sh', 'content': args[1]}]
    })
    output = res.json()['run']['output'].rstrip('\n')
    irc.msg(args[0], f'{hostmask[0]}: {output or "(no output)"}')


LUA_CODE = r"""
local f = assert(io.open("code.lua", "rb"))
local code = f:read("*a")
f:close()
local f = load("return " .. code)
if f then
    print(f())
else
    dofile("code.lua")
end
"""


@register_command('lua')
def lua(irc, hostmask, is_admin, args):
    res = requests.post(PISTON_URL, json={
        'language': 'lua',
        'version': '*',
        'files': [
            {'name': 'init.lua', 'content': LUA_CODE},
            {'name': 'code.lua', 'content': args[1]}
        ]
    })
    output = res.json()['run']['output'].rstrip('\n')
    irc.msg(args[0], f'{hostmask[0]}: {output or "(no output)"}')


PYTHON_CODE = r"""
import ast, builtins

with open('code.py', 'r') as f:
    code = f.read()


# Automatically import libraries where possible
class _BuiltinsWrapper(dict):
    __slots__ = ()
    def __missing__(self, key):
        try:
            return __import__(key)
        except ImportError:
            raise NameError(f'name {key!r} is not defined')


env = {'__builtins__': _BuiltinsWrapper(builtins.__dict__), 'code': code}


try:
    ast.parse(code, mode='eval')
except SyntaxError:
    exec(code, env)
else:
    print(eval(code, env))
"""


@register_command('py', 'py3', 'python', 'python3')
def py3(irc, hostmask, is_admin, args):
    res = requests.post(PISTON_URL, json={
        'language': 'python',
        'version': '3',
        'files': [
            {'name': 'main.py', 'content': PYTHON_CODE},
            {'name': 'code.py', 'content': args[1]}
        ]
    })
    run = res.json()['run']
    output = run['output'].rstrip('\n')
    if run['code'] == 1:
        output = output.rsplit('\n', 1)[-1]
    irc.msg(args[0], f'{hostmask[0]}: {output or "(no output)"}')


@register_command('hs', 'haskell')
def hs(irc, hostmask, is_admin, args):
    res = requests.post(PISTON_URL, json={
        'language': 'haskell',
        'version': '*',
        'files': [{'name': 'main.hs', 'content': args[1]}]
    })
    output = res.json()['run']['output'].rstrip('\n')
    irc.msg(args[0], f'{hostmask[0]}: {output or "(no output)"}')