summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJack Jansen <jack.jansen@cwi.nl>2000-11-29 10:02:22 (GMT)
committerJack Jansen <jack.jansen@cwi.nl>2000-11-29 10:02:22 (GMT)
commitb5ec5e4b41554250ec3381f7193ee4d1bbd0eab2 (patch)
treedbc256c2e5268540af47c5872151f8b50c3bfec9
parentf65ab1bf100f4a90a465ce2c60015228d480c83b (diff)
downloadcpython-b5ec5e4b41554250ec3381f7193ee4d1bbd0eab2.zip
cpython-b5ec5e4b41554250ec3381f7193ee4d1bbd0eab2.tar.gz
cpython-b5ec5e4b41554250ec3381f7193ee4d1bbd0eab2.tar.bz2
Contributed code that converts Python source files to any combination of tabs/spaces for indenting.
-rw-r--r--Mac/Contrib/Tabcleaner/Tabcleaner.README41
-rw-r--r--Mac/Contrib/Tabcleaner/Tabcleaner.py160
2 files changed, 201 insertions, 0 deletions
diff --git a/Mac/Contrib/Tabcleaner/Tabcleaner.README b/Mac/Contrib/Tabcleaner/Tabcleaner.README
new file mode 100644
index 0000000..821f7e1
--- /dev/null
+++ b/Mac/Contrib/Tabcleaner/Tabcleaner.README
@@ -0,0 +1,41 @@
+Original README for Tabcleaner.py
+
+tabcleaner.py is a utility that reformats leading whitespace in a Python source.
+It uses tokenize.py (from the std distribution) to detect INDENTs and DEDENTs,
+then reformats according to the user's options (tabs-only, spaces-only with
+indent size n, or mixed with tab worth m and indent level of n).
+
+Python does not care about the indent of comments and multi-linestrings.
+tabcleaner places these at what Python considers the current indentlevel. About
+half the time, this is correct; the rest of the time it is probably one indent
+level less than what was desired. It is pretty much guaranteed to be
+syntactically correct, (earlier versions broke on some triple-quoted strings).
+
+With no args, (or "-h") prints usage text.
+
+Contact: gmcm@hypernet.com
+
+Additional comments: I have made a few slight changes. It was written to take
+command line arguments, so that you can set parameters like the size of indents,
+and whether you want the result to be all tabs, or all spaces, or a mixture of
+both (an evil combination, if you ask me). It is set, be default, to change your
+indentation to all tabs.
+
+In the current version of Python, all the code in the standard library is
+indented with only spaces. This is a somewhat awkward standard on the mac, so
+most MacPython code is indented with only tabs. This script can be used to do any
+version, but all tabs is the default, which seems to be the best option for the
+Mac.
+
+How to use it on a Mac:
+
+The script is set up to take filenames (or directory names) on the command line.
+To simulate this behaviour with MacPython, you can build an applet out of it
+(with BuildApplet, which should be in your Python folder). Any files draggged and
+dropped onto the resulting applet will be converted to all tabs, with a backup
+copy havning been saved.
+
+If you want the script to convert to space based indentation, your best bet is
+probably to change the default on line 46 of the file.
+
+-Chris Barker cbarker@jps.net
diff --git a/Mac/Contrib/Tabcleaner/Tabcleaner.py b/Mac/Contrib/Tabcleaner/Tabcleaner.py
new file mode 100644
index 0000000..c6d3223
--- /dev/null
+++ b/Mac/Contrib/Tabcleaner/Tabcleaner.py
@@ -0,0 +1,160 @@
+#!/usr/bin/python
+
+import tokenize
+import string
+
+TABSONLY = 'TABSONLY'
+SPACESONLY = 'SPACESONLY'
+MIXED = 'MIXED'
+
+class PyText:
+ def __init__(self, fnm, optdict):
+ self.optdict = optdict
+ self.fnm = fnm
+ self.txt = open(self.fnm, 'r').readlines()
+ self.indents = [(0, 0, )]
+ self.lnndx = 0
+ self.indentndx = 0
+ def getline(self):
+ if self.lnndx < len(self.txt):
+ txt = self.txt[self.lnndx]
+ self.lnndx = self.lnndx + 1
+ else:
+ txt = ''
+ return txt
+ def tokeneater(self, type, token, start, end, line):
+ if type == tokenize.INDENT:
+ (lvl, s) = self.indents[-1]
+ self.indents[-1] = (lvl, s, start[0]-1)
+ self.indents.append((lvl+1, start[0]-1,))
+ elif type == tokenize.DEDENT:
+ (lvl, s) = self.indents[-1]
+ self.indents[-1] = (lvl, s, start[0]-1)
+ self.indents.append((lvl-1, start[0]-1,))
+ elif type == tokenize.ENDMARKER:
+ (lvl, s) = self.indents[-1]
+ self.indents[-1] = (lvl, s, len(self.txt))
+ def split(self, ln):
+ content = string.lstrip(ln)
+ if not content:
+ return ('', '\n')
+ lead = ln[:len(ln) - len(content)]
+ lead = string.expandtabs(lead)
+ return (lead, content)
+
+ def process(self):
+ style = self.optdict.get('style', TABSONLY)
+ indent = string.atoi(self.optdict.get('indent', '4'))
+ tabsz = string.atoi(self.optdict.get('tabs', '8'))
+ print 'file %s -> style %s, tabsize %d, indent %d' % (self.fnm, style, tabsz, indent)
+ tokenize.tokenize(self.getline, self.tokeneater)
+ #import pprint
+ #pprint.pprint(self.indents)
+ new = []
+ for (lvl, s, e) in self.indents:
+ if s >= len(self.txt):
+ break
+ if s == e:
+ continue
+ oldlead, content = self.split(self.txt[s])
+ #print "oldlead", len(oldlead), `oldlead`
+ if style == TABSONLY:
+ newlead = '\t'*lvl
+ elif style == SPACESONLY:
+ newlead = ' '*(indent*lvl)
+ else:
+ sz = indent*lvl
+ t,spcs = divmod(sz, tabsz)
+ newlead = '\t'*t + ' '*spcs
+ new.append(newlead + content)
+ for ln in self.txt[s+1:e]:
+ lead, content = self.split(ln)
+ #print "lead:", len(lead)
+ new.append(newlead + lead[len(oldlead):] + content)
+ self.save(new)
+ #print "---", self.fnm
+ #for ln in new:
+ # print ln,
+ #print
+
+ def save(self, txt):
+ bakname = os.path.splitext(self.fnm)[0]+'.bak'
+ print "backing up", self.fnm, "to", bakname
+ #print os.getcwd()
+ try:
+ os.rename(self.fnm, bakname)
+ except os.error:
+ os.remove(bakname)
+ os.rename(self.fnm, bakname)
+ open(self.fnm, 'w').writelines(txt)
+
+def test():
+ tc = PyText('test1.py')
+ tc.process()
+ tc = PyText('test1.py')
+ tc.process(style=TABSONLY)
+ tc = PyText('test1.py')
+ tc.process(style=MIXED, indent=4, tabs=8)
+ tc = PyText('test1.py')
+ tc.process(style=MIXED, indent=2, tabs=8)
+
+def cleanfile(fnm, d):
+ if os.path.isdir(fnm) and not os.path.islink(fnm):
+ names = os.listdir(fnm)
+ for name in names:
+ fullnm = os.path.join(fnm, name)
+ if (os.path.isdir(fullnm) and not os.path.islink(fullnm)) or \
+ os.path.normcase(fullnm[-3:]) == ".py":
+ cleanfile(fullnm, d)
+ return
+ tc = PyText(fnm, d)
+ tc.process()
+
+usage="""\
+%s [options] [path...]
+ options
+ -T : reformat to TABS ONLY
+ -S : reformat to SPACES ONLY ( -i option is important)
+ -M : reformat to MIXED SPACES / TABS ( -t and -i options important)
+ -t<n> : tab is worth <n> characters
+ -i<n> : indents should be <n> characters
+ -h : print this text
+ path is file or directory
+"""
+if __name__ == '__main__':
+ import sys, getopt, os
+ opts, args = getopt.getopt(sys.argv[1:], "TSMht:i:")
+ d = {}
+ print `opts`
+ for opt in opts:
+ if opt[0] == '-T':
+ d['style'] = TABSONLY
+ elif opt[0] == '-S':
+ d['style'] = SPACESONLY
+ elif opt[0] == '-M':
+ d['style'] = MIXED
+ elif opt[0] == '-t':
+ d['tabs'] = opt[1]
+ elif opt[0] == '-i':
+ d['indent'] = opt[1]
+ elif opt[0] == '-h':
+ print usage % sys.argv[0]
+ sys.exit(0)
+ if not args:
+ print usage % sys.argv[0]
+ for arg in args:
+ cleanfile(arg, d)
+
+
+
+
+
+
+
+
+
+
+
+
+
+