Skip to content

Commit

Permalink
Merge remote-tracking branch 'origin/github/pr/2'
Browse files Browse the repository at this point in the history
  • Loading branch information
mika committed Jun 9, 2020
2 parents bc8d681 + 7d13ed6 commit 508d788
Show file tree
Hide file tree
Showing 3 changed files with 153 additions and 152 deletions.
2 changes: 2 additions & 0 deletions Makefile
Expand Up @@ -21,3 +21,5 @@ clean:
@for i in $(MANPAGES); do \
rm -f $$i.html $$i.xml $$i.gz; done

lint:
flake8 --max-line-length=120 grml-paste
2 changes: 1 addition & 1 deletion debian/control
Expand Up @@ -13,7 +13,7 @@ Bugs: mailto:bugs@grml.org

Package: grml-paste
Architecture: all
Depends: ${shlibs:Depends}, ${misc:Depends}, python
Depends: ${shlibs:Depends}, ${misc:Depends}, python3
Description: command line interface for paste.grml.org
This package provides a command line interface tool to upload
plain text to http://paste.grml.org/ - being the official paste
Expand Down
301 changes: 150 additions & 151 deletions grml-paste
@@ -1,146 +1,143 @@
#!/usr/bin/python
#!/usr/bin/python3
# Filename: grml-paste
# Purpose: XmlRpc interface client to paste.grml.org
# Author: Michael Gebetsroither <gebi@grml.org>
# License: This file is licensed under the GPL v2.
################################################################################

import sys
import xmlrpclib
from xmlrpc.client import ServerProxy
import optparse
import inspect
import getpass

# program defaults
DEFAULT_SERVER='http://paste.grml.org/server.pl'
DEFAULT_SERVER = "http://paste.grml.org/server.pl"


class ActionFailedException(Exception):
'''Thrown if server returned an error'''
"""Thrown if server returned an error"""

def __init__(self, errormsg, ret):
Exception.__init__(self, errormsg, ret)

def what(self):
'''Get errormessage'''
"""Get errormessage"""
return self.args[0]

def dwhat(self):
'''Get more verbose errormessage'''
"""Get more verbose errormessage"""
return self.args[1]


class Action(object):
def __init__(self, args, opts):
self.args_ = args
self.opts_ = opts

def _createProxy(self):
return xmlrpclib.ServerProxy(self.opts_.server, verbose=False)

def _callProxy(self, functor, server=None):
'''Wrapper for xml-rpc calls to server which throws an
ActionFailedException on error'''
if server is None:
server = self._createProxy()
ret = functor(server)
if ret['rc'] != 0:
raise ActionFailedException(ret['statusmessage'], ret)
return ret

def call(self, method_name):
'''External Interface to call the appropriate action'''
return self.__getattribute__(method_name)()

def actionAddPaste(self):
'''Add paste to the server: <1.line> <2.line> ...
default Read paste from stdin.
[text] Every argument on the commandline will be interpreted as
a seperate line of paste.
'''
server = self._createProxy()
o = self.opts_
code = self.args_
if len(self.args_) == 0:
code = [ i.rstrip() for i in sys.stdin.readlines() ]
code = '\n'.join(code)
result = self._callProxy(lambda s: s.paste.addPaste(code, o.name, o.expire * 3600, o.lang, o.private),
server)
return (result['statusmessage'], result)

def actionDelPaste(self):
'''Delete paste from server: <digest>
<digest> Digest of paste you want to remove.
'''
digest = self.args_.pop(0)
result = self._callProxy(lambda s: s.paste.deletePaste(digest))
return (result['statusmessage'], result)

def actionGetPaste(self):
'''Get paste from server: <id>
<id> Id of paste you want to receive.
'''
id = self.args_.pop(0)
result = self._callProxy(lambda s: s.paste.getPaste(id))
return (result['code'], result)

def actionGetLangs(self):
'''Get supported language highlighting types from server'''
result = self._callProxy(lambda s: s.paste.getLanguages())
return ('\n'.join(result['langs']), result)

def actionAddShortUrl(self):
'''Add short-URL: <url>
<url> Short-URL to add
'''
url = self.args_.pop(0)
result = self._callProxy(lambda s: s.paste.addShortURL(url))
return (result['url'], result)

def actionGetShortUrl(self):
'''Resolve short-URL: <url>
<url> Short-URL to get clicks of
'''
url = self.args_.pop(0)
result = self._callProxy(lambda s: s.paste.resolveShortURL(url))
return (result['url'], result)

def actionGetShortUrlClicks(self):
'''Get clicks of short-URL: <url>
<url> Short-URL to get clicks of
'''
url = self.args_.pop(0)
result = self._callProxy(lambda s: s.paste.ShortURLClicks(url))
return (result['count'], result)

def actionHelp(self):
'''Print more verbose help about specific action: <action>
<action> Topic on which you need more verbose help.
'''
if len(self.args_) < 1:
alias = "help"
else:
alias = self.args_.pop(0)

if alias in actions:
fun = actions[alias]
print inspect.getdoc(self.__getattribute__(fun))
print "\naliase: " + " ".join([i for i in actions_r[fun] if i != alias])
else:
print "Error: No such command - %s" % (alias)
OPT_PARSER.print_usage()
sys.exit(0)


# actionAddPaste -> [add, a]
def _paste(opts):
"""Get paste proxy object"""
return (ServerProxy(opts.server, verbose=False).paste)


def _check_success(return_data):
"""Check if call was successful, raise AcitonFailedException otherwise"""
if return_data["rc"] != 0:
raise ActionFailedException(return_data["statusmessage"], return_data)
return return_data


def action_add_paste(opts, code):
"""Add paste to the server: <1.line> <2.line> ...
default Read paste from stdin.
[text] Every argument on the commandline will be interpreted as
a seperate line of paste.
"""
if len(code) == 0:
code = [line.rstrip() for line in sys.stdin.readlines()]
code = "\n".join(code)
result = _check_success(_paste(opts).addPaste(code, opts.name, opts.expire * 3600, opts.lang, opts.private))
return result["statusmessage"], result


def action_del_paste(opts, args):
"""Delete paste from server: <digest>
<digest> Digest of paste you want to remove.
"""
digest = args.pop(0)
result = _check_success(_paste(opts).deletePaste(digest))
return result["statusmessage"], result


def action_get_paste(opts, args):
"""Get paste from server: <id>
<id> Id of paste you want to receive.
"""
paste_id = args.pop(0)
result = _check_success(_paste(opts).getPaste(paste_id))
return result["code"], result


def action_get_langs(opts, args):
"""Get supported language highlighting types from server"""
result = _check_success(_paste(opts).getLanguages())
return "\n".join(result["langs"]), result


def action_add_short_url(opts, args):
"""Add short-URL: <url>
<url> Short-URL to add
"""
url = args.pop(0)
result = _check_success(_paste(opts).addShortURL(url))
return result["url"], result


def action_get_short_url(opts, args):
"""Resolve short-URL: <url>
<url> Short-URL to get clicks of
"""
url = args.pop(0)
result = _check_success(_paste(opts).resolveShortURL(url))
return result["url"], result


def action_get_short_url_clicks(opts, args):
"""Get clicks of short-URL: <url>
<url> Short-URL to get clicks of
"""
url = args.pop(0)
result = _check_success(_paste(opts).ShortURLClicks(url))
return result["count"], result


def action_help(opts, args):
"""Print more verbose help about specific action: <action>
<action> Topic on which you need more verbose help.
"""
if len(args) < 1:
alias = "help"
else:
alias = args.pop(0)

if alias in actions:
function_name = actions[alias]
print(inspect.getdoc(globals()[function_name]))
print("\naliases: " + " ".join([i for i in actions_r[function_name] if i != alias]))
else:
print("Error: No such command - %s" % (alias))
OPT_PARSER.print_usage()
sys.exit(0)


# action_add_paste -> [add, a]
actions_r = {}

# add -> actionAddPaste
# a -> actionAddPaste
actions = {}
# add -> action_add_paste
# a -> action_add_paste
actions = {}

# option parser
OPT_PARSER = None
Expand All @@ -150,55 +147,57 @@ OPT_PARSER = None
# MAIN
##
if __name__ == "__main__":
action_spec = ['actionAddPaste add a',
'actionDelPaste del d rm',
'actionGetPaste get g',
'actionGetLangs getlangs gl langs l',
'actionAddShortUrl addurl',
'actionGetShortUrl geturl',
'actionGetShortUrlClicks getclicks',
'actionHelp help']
for i in action_spec:
aliases = i.split()
action_specs = [
"action_add_paste add a",
"action_del_paste del d rm",
"action_get_paste get g",
"action_get_langs getlangs gl langs l",
"action_add_short_url addurl",
"action_get_short_url geturl",
"action_get_short_url_clicks getclicks",
"action_help help"
]
for action_spec in action_specs:
aliases = action_spec.split()
cmd = aliases.pop(0)
actions_r[cmd] = aliases
for (k,v) in actions_r.items():
for (action_name, v) in actions_r.items():
for i in v:
actions[i] = k
actions[i] = action_name

usage = "usage: %prog [options] ACTION <args>\n\n" +\
"actions:\n" +\
"\n".join(["%12s\t%s" % (v[0], inspect.getdoc(getattr(Action, k)).split('\n')[0]) \
for (k,v) in actions_r.items()])
"\n".join(["%12s\t%s" % (v[0], inspect.getdoc(globals()[action_name]).splitlines()[0])
for (action_name, v) in actions_r.items()])
running_user = getpass.getuser()
parser = optparse.OptionParser(usage=usage)
parser.add_option('-n', '--name', default=running_user, help="Name of poster")
parser.add_option('-e', '--expire', type=int, default=72, metavar='HOURS',
help='Time at wich paste should expire')
parser.add_option('-l', '--lang', default='Plain', help='Type of language to highlight')
parser.add_option("-n", "--name", default=running_user, help="Name of poster")
parser.add_option("-e", "--expire", type=int, default=72, metavar="HOURS",
help="Time at wich paste should expire")
parser.add_option("-l", "--lang", default="Plain", help="Type of language to highlight")
parser.add_option("-p", "--private", action="count", dest="private", default=0,
help='Create hidden paste'),
parser.add_option('-s', '--server', default=DEFAULT_SERVER,
help='Paste server')
parser.add_option('-v', '--verbose', action='count', default=0, help='More output')
help="Create hidden paste"),
parser.add_option("-s", "--server", default=DEFAULT_SERVER,
help="Paste server")
parser.add_option("-v", "--verbose", action="count", default=0, help="More output")
(opts, args) = parser.parse_args()
OPT_PARSER = parser

if len(args) == 0:
parser.error('Please provide me with an action')
parser.error("Please provide me with an action")
elif args[0] in actions:
cmd = args.pop(0)
action = Action(args, opts)
action = actions[cmd]
try:
(msg, ret) = action.call(actions[cmd])
(msg, ret) = globals()[action](opts, args)
if opts.verbose == 0:
print msg
print(msg)
else:
print ret
except ActionFailedException, e:
sys.stderr.write('Server Error: %s\n' % e.what())
if opts.verbose >0:
print e.dwhat()
print(ret)
except ActionFailedException as except_inst:
sys.stderr.write("Server Error: %s\n" % except_inst.what())
if opts.verbose > 0:
print(except_inst.dwhat())
sys.exit(1)
else:
parser.error('Unknown action: %s' % args[0])
parser.error("Unknown action: %s" % args[0])

0 comments on commit 508d788

Please sign in to comment.