├── LICENSE ├── README └── bin ├── find-pip-installed-licenses ├── json-tool ├── open-smb-share └── unp /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2011 by Armin Ronacher. 2 | 3 | Some rights reserved. 4 | 5 | Redistribution and use in source and binary forms, with or without 6 | modification, are permitted provided that the following conditions are 7 | met: 8 | 9 | * Redistributions of source code must retain the above copyright 10 | notice, this list of conditions and the following disclaimer. 11 | 12 | * Redistributions in binary form must reproduce the above 13 | copyright notice, this list of conditions and the following 14 | disclaimer in the documentation and/or other materials provided 15 | with the distribution. 16 | 17 | * The names of the contributors may not be used to endorse or 18 | promote products derived from this software without specific 19 | prior written permission. 20 | 21 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 22 | "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 23 | LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 24 | A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 25 | OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 26 | SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 27 | LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 28 | DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 29 | THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 30 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 31 | OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 32 | -------------------------------------------------------------------------------- /README: -------------------------------------------------------------------------------- 1 | Various command line utilities. 2 | 3 | unp unpacks things 4 | json-tool colorizes JSON 5 | find-pip-installed-licenses prints license info from pip 6 | open-smb-share takes a \\unc path and opens it in finder 7 | -------------------------------------------------------------------------------- /bin/find-pip-installed-licenses: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | from pkg_resources import working_set 3 | 4 | LICENSE_LINE = 'Classifier: License :: ' 5 | 6 | LICENSE_GROUP = { 7 | 'DFSG approved': 'DFSG', 8 | 'OSI Approved': 'OSI', 9 | } 10 | 11 | GPL_FAMILY = set([ 12 | 'OSI Approved :: GNU Affero General Public License v3', 13 | 'OSI Approved :: GNU Affero General Public License v3 or later (AGPLv3+)', 14 | #'OSI Approved :: GNU Free Documentation License (FDL)', 15 | 'OSI Approved :: GNU General Public License (GPL)', 16 | 'OSI Approved :: GNU General Public License v2 (GPLv2)', 17 | 'OSI Approved :: GNU General Public License v2 or later (GPLv2+)', 18 | 'OSI Approved :: GNU General Public License v3 (GPLv3)', 19 | 'OSI Approved :: GNU General Public License v3 or later (GPLv3+)', 20 | #'OSI Approved :: GNU Lesser General Public License v2 (LGPLv2)', 21 | #'OSI Approved :: GNU Lesser General Public License v2 or later (LGPLv2+)', 22 | #'OSI Approved :: GNU Lesser General Public License v3 (LGPLv3)', 23 | #'OSI Approved :: GNU Lesser General Public License v3 or later (LGPLv3+)', 24 | #'OSI Approved :: GNU Library or Lesser General Public License (LGPL)', 25 | ]) 26 | 27 | QUESTIONABLE_LICENSES = set([ 28 | 'OSI Approved :: MITRE Collaborative Virtual Workspace License (CVW)', 29 | 'OSI Approved :: Motosoto License', 30 | 'OSI Approved :: Ricoh Source Code Public License', 31 | ]) 32 | 33 | LICENSE_MAPPING = { 34 | 'Aladdin Free Public License (AFPL)': 'Aladdin Free Public License', 35 | 'CC0 1.0 Universal (CC0 1.0) Public Domain Dedication': 'CC0 1.0', 36 | 'Eiffel Forum License (EFL)': 'Eiffel Forum License', 37 | 'Netscape Public License (NPL)': 'Netscape Public License', 38 | 'Nokia Open Source License (NOKOS)': 'Nokia Open Source License', 39 | 'OSI Approved :: Academic Free License (AFL)': 'Academic Free License', 40 | 'OSI Approved :: Apache Software License': 'Apache Software License', 41 | 'OSI Approved :: Apple Public Source License': 'Apple Public Source License', 42 | 'OSI Approved :: Artistic License': 'Artistic License', 43 | 'OSI Approved :: Attribution Assurance License': 'Attribution Assurance License', 44 | 'OSI Approved :: BSD License': 'BSD', 45 | 'OSI Approved :: Common Public License': 'Common Public License', 46 | 'OSI Approved :: Eiffel Forum License': 'Eiffel Forum License', 47 | 'OSI Approved :: European Union Public Licence 1.0 (EUPL 1.0)': 'European Union Public License 1.0', 48 | 'OSI Approved :: European Union Public Licence 1.1 (EUPL 1.1)': 'European Union Public License 1.1', 49 | 'OSI Approved :: GNU Affero General Public License v3': 'GNU AGPLv3', 50 | 'OSI Approved :: GNU Affero General Public License v3 or later (AGPLv3+)': 'GNU AGPLv3+', 51 | 'OSI Approved :: GNU Free Documentation License (FDL)': 'FDL', 52 | 'OSI Approved :: GNU General Public License (GPL)': 'GNU GPL', 53 | 'OSI Approved :: GNU General Public License v2 (GPLv2)': 'GNU GPLv2', 54 | 'OSI Approved :: GNU General Public License v2 or later (GPLv2+)': 'GNU GPLv2+', 55 | 'OSI Approved :: GNU General Public License v3 (GPLv3)': 'GNU GPLv3', 56 | 'OSI Approved :: GNU General Public License v3 or later (GPLv3+)': 'GNU GPLv3+', 57 | 'OSI Approved :: GNU Lesser General Public License v2 (LGPLv2)': 'GNU LGPLv2', 58 | 'OSI Approved :: GNU Lesser General Public License v2 or later (LGPLv2+)': 'GNU LGPLv2+', 59 | 'OSI Approved :: GNU Lesser General Public License v3 (LGPLv3)': 'GNU LGPLv3', 60 | 'OSI Approved :: GNU Lesser General Public License v3 or later (LGPLv3+)': 'GNU LGPLv3+', 61 | 'OSI Approved :: GNU Library or Lesser General Public License (LGPL)': 'GNU LGPL', 62 | 'OSI Approved :: IBM Public License': 'IBM Public License', 63 | 'OSI Approved :: Intel Open Source License': 'Intel Open Source License', 64 | 'OSI Approved :: ISC License (ISCL)': 'ISIC License', 65 | 'OSI Approved :: Jabber Open Source License': 'Jabber Open Source License', 66 | 'OSI Approved :: MIT License': 'MIT', 67 | 'OSI Approved :: MITRE Collaborative Virtual Workspace License (CVW)': 'MITRE Collaborative Virtual Workspace License', 68 | 'OSI Approved :: Motosoto License': 'Motosoto License', 69 | 'OSI Approved :: Mozilla Public License 1.0 (MPL)': 'MPL 1.0', 70 | 'OSI Approved :: Mozilla Public License 1.1 (MPL 1.1)': 'MPL 1.1', 71 | 'OSI Approved :: Mozilla Public License 2.0 (MPL 2.0)': 'MPL 2.0', 72 | 'OSI Approved :: Nethack General Public License': 'Nethack General Public License', 73 | 'OSI Approved :: Nokia Open Source License': 'Nokia Open Source License', 74 | 'OSI Approved :: Open Group Test Suite License': 'Open Group Test Suite License', 75 | 'OSI Approved :: Python License (CNRI Python License)': 'Python License', 76 | 'OSI Approved :: Python Software Foundation License': 'Python Softare Foundation License', 77 | 'OSI Approved :: Qt Public License (QPL)': 'Qt Public License', 78 | 'OSI Approved :: Ricoh Source Code Public License': 'Ricoh Source Code Public License', 79 | 'OSI Approved :: Sleepycat License': 'Sleepycat License', 80 | 'OSI Approved :: Sun Industry Standards Source License (SISSL)': 'SISSL', 81 | 'OSI Approved :: Sun Public License': 'Sun Public License', 82 | 'OSI Approved :: University of Illinois/NCSA Open Source License': 'University of Illinois/NCSA Open Source License', 83 | 'OSI Approved :: Vovida Software License 1.0': 'Vovida Software License 1.0', 84 | 'OSI Approved :: W3C License': 'W3C License', 85 | 'OSI Approved :: X.Net License': 'X.Net License', 86 | 'OSI Approved :: zlib/libpng License': 'zlib', 87 | 'OSI Approved :: Zope Public License': 'Zope Public License', 88 | 'Public Domain': 'Public Domain', 89 | 'Repoze Public License': 'Repoze Public License', 90 | } 91 | 92 | 93 | def find_licenses(): 94 | for distribution in working_set: 95 | pkg_info = distribution.get_metadata('PKG-INFO') 96 | licenses = [] 97 | if pkg_info: 98 | for line in pkg_info.splitlines(): 99 | if line.startswith(LICENSE_LINE): 100 | licenses.append(line[len(LICENSE_LINE):].lstrip()) 101 | if not licenses: 102 | licenses = [] 103 | short_licenses = set() 104 | is_gpl = False 105 | fallback_group = 'Unknown' 106 | for license in licenses: 107 | if license in LICENSE_GROUP: 108 | fallback_group = LICENSE_GROUP[license] 109 | short_name = LICENSE_MAPPING.get(license) 110 | if short_name is None: 111 | short_name = license 112 | short_licenses.add(short_name) 113 | if license in GPL_FAMILY: 114 | is_gpl = True 115 | if not short_licenses: 116 | short_licenses.add(fallback_group) 117 | yield distribution.egg_name(), { 118 | 'licenses': sorted(short_licenses), 119 | 'is_gpl': is_gpl, 120 | } 121 | 122 | 123 | def main(): 124 | license_groups = {} 125 | gpl_touched = set() 126 | for egg, info in find_licenses(): 127 | for license in info['licenses']: 128 | license_groups.setdefault(license, set()).add(egg) 129 | if info['is_gpl']: 130 | gpl_touched.add(egg) 131 | 132 | license_groups = sorted(license_groups.items()) 133 | for license, eggs in license_groups: 134 | print license 135 | for egg in sorted(eggs): 136 | print ' %s' % egg 137 | 138 | if gpl_touched: 139 | print 140 | print 'GPL touched:' 141 | for egg in sorted(gpl_touched): 142 | print ' %s' % egg 143 | 144 | 145 | if __name__ == '__main__': 146 | main() 147 | -------------------------------------------------------------------------------- /bin/json-tool: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | """ 4 | json-tool 5 | ~~~~~~~~~ 6 | 7 | JSON command line utility. Can pretty print JSON 8 | and doe some other things with it such as selecting 9 | items from sequences or objects. 10 | 11 | Select:: 12 | 13 | { 14 | "items": [{"foo": 1}, {"foo": 2}] 15 | } 16 | 17 | items.foo 18 | 19 | :copyright: (c) Copyright 2011 by Armin Ronacher. 20 | :license: BSD, see LICENSE for more details. 21 | """ 22 | import sys 23 | from optparse import OptionParser 24 | from StringIO import StringIO 25 | 26 | try: 27 | import simplejson as json 28 | except ImportError: 29 | import json 30 | 31 | 32 | try: 33 | from pygments import highlight 34 | from pygments.formatters import TerminalFormatter 35 | from pygments.lexers import JavascriptLexer 36 | have_pygments = True 37 | except ImportError: 38 | have_pygments = False 39 | 40 | 41 | def print_formatted_json(stream, json_data, indentation): 42 | formatted = json.dumps(json_data, indent=indentation) 43 | if have_pygments and getattr(stream, 'isatty', lambda: False)(): 44 | formatted = highlight(formatted, formatter=TerminalFormatter(), 45 | lexer=JavascriptLexer()).rstrip() 46 | print >> stream, formatted 47 | 48 | 49 | def main(): 50 | parser = OptionParser() 51 | parser.add_option('-i', '--indentation', dest='indent', type=int, 52 | default=2, 53 | help='Number of spaces to use for indentation') 54 | parser.add_option('-l', '--list-process', dest='list_process', 55 | action='store_true', help='process on a line ' 56 | 'separated list of JSON objects') 57 | parser.add_option('-T', '--strip-tab', dest='strip_tab', 58 | action='store_true', 59 | help='Strip up to leading tab when doing list processing') 60 | parser.add_option('-t', '--strip-and-print=tab', dest='strip_and_print_tab', 61 | action='store_true', help='Like -T but prints') 62 | parser.add_option('-N', '--extra-newline', dest='extra_newline', 63 | action='store_true', help='print an extra ' 64 | 'newline at the end') 65 | options, args = parser.parse_args() 66 | if len(args) > 1: 67 | parser.error('Too many arguments') 68 | elif not args: 69 | stream = sys.stdin 70 | else: 71 | stream = open(args[0]) 72 | 73 | def highlight(stream): 74 | try: 75 | json_data = json.load(stream) 76 | except Exception, e: 77 | parser.error('Could not read json:\n %s' % e) 78 | print_formatted_json(sys.stdout, json_data, options.indent) 79 | if options.extra_newline: 80 | sys.stdout.write('\n') 81 | 82 | if options.list_process: 83 | for line in stream: 84 | if options.strip_tab or options.strip_and_print_tab: 85 | if '\t' in line: 86 | tab, line = line.split('\t', 1) 87 | if options.strip_and_print_tab: 88 | sys.stdout.write(tab + '\t') 89 | highlight(StringIO(line)) 90 | else: 91 | highlight(stream) 92 | 93 | 94 | if __name__ == '__main__': 95 | main() 96 | -------------------------------------------------------------------------------- /bin/open-smb-share: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | import sys 3 | import subprocess 4 | from urllib import quote 5 | 6 | 7 | def main(): 8 | if len(sys.argv) != 2: 9 | print 'error: invalid number of arguments' 10 | return 11 | path = sys.argv[1] 12 | path = path.lstrip('\\\\').split('\\') 13 | for idx, item in enumerate(path): 14 | path[idx] = quote(item) 15 | subprocess.call(['open', 'smb://' + '/'.join(path)]) 16 | 17 | 18 | if __name__ == '__main__': 19 | main() 20 | -------------------------------------------------------------------------------- /bin/unp: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | # unp 3 | # ~~~ 4 | # 5 | # Helper script for unpacking archives of any kind. 6 | # It detects the archive by file extension so make 7 | # 8 | # :copyright: (c) Copyright 2011 by Armin Ronacher 9 | # :license: BSD, see LICENSE for more details 10 | # 11 | 12 | if [ x == x$1 ]; then 13 | echo 'usage: unp [filenames]' 14 | else 15 | 16 | # Check for GNU Tar on systems that don't have it by default. (Solaris) 17 | type "gtar" &>/dev/null; 18 | 19 | if [ $? == 0 ]; then 20 | TAR=gtar 21 | else 22 | TAR=tar 23 | fi 24 | 25 | for fn in "$@"; do 26 | if [ -f "$fn" ]; then 27 | case "$fn" in 28 | *.tar.gz) $TAR xvzf "$fn" ;; 29 | *.tgz) $TAR xvzf "$fn" ;; 30 | *.tar.bz2) $TAR xvjf "$fn" ;; 31 | *.gz) gunzip "$fn" ;; 32 | *.bz2) bunzip2 "$fn" ;; 33 | *.tar) $TAR xvf "$fn" ;; 34 | *.zip|*.egg|*.jar|*.whl) unzip "$fn" ;; 35 | *.rar) unrar e "$fn" ;; 36 | *.7z) 7z x "$fn" ;; 37 | *) echo "error: '$fn' is an unknown archive" ;; 38 | esac 39 | else 40 | echo "error: '$fn' is not a valid archive" 41 | fi 42 | done 43 | fi 44 | --------------------------------------------------------------------------------