ArielGlenn has submitted this change and it was merged.
Change subject: move cli static methods out to separate file
......................................................................
move cli static methods out to separate file
Change-Id: I3db85c76ea268ff57b77fcff9b3f6873d44dbaab
---
M dataretention/retention/cli.py
A dataretention/retention/cliutils.py
2 files changed, 185 insertions(+), 178 deletions(-)
Approvals:
ArielGlenn: Verified; Looks good to me, approved
diff --git a/dataretention/retention/cli.py b/dataretention/retention/cli.py
index 5fb1848..4394ac5 100644
--- a/dataretention/retention/cli.py
+++ b/dataretention/retention/cli.py
@@ -4,7 +4,6 @@
import json
import runpy
import readline
-import atexit
import traceback
sys.path.append('/srv/audits/retention/scripts/')
@@ -22,7 +21,7 @@
import retention.fileutils
import retention.ruleutils
from retention.userconfretriever import RemoteUserCfRetriever
-
+import retention.cliutils
class CommandLine(object):
'''
@@ -46,7 +45,7 @@
self.basedir = None
self.current_dir = None
self.prompt = None
- CommandLine.init_readline_hist()
+ retention.cliutils.init_readline_hist()
self.hostlist = None
self.dirs_problem = None
self.dirs_skipped = None
@@ -137,23 +136,6 @@
self.perhost_ignores[host]['files']['/'] = (
self.perhost_rules_from_file['ignored_files'][host])
- @staticmethod
- def init_readline_hist():
- readline.parse_and_bind("tab: complete")
- histfile = os.path.join(os.path.expanduser("~"), ".audit_hist")
- try:
- readline.read_history_file(histfile)
- except IOError:
- pass
- atexit.register(readline.write_history_file, histfile)
- # also fix up delims so we don't have annoying dir elt behavior
- delims = readline.get_completer_delims()
- delims = delims.replace("/", "")
- readline.set_completer_delims(delims)
-
- def save_history(self, histfile):
- readline.write_history_file(histfile)
-
def host_completion(self, text, state):
if text == "":
matches = self.hostlist
@@ -186,11 +168,11 @@
return host_todo
else:
print "Please choose one of the following hosts:"
- CommandLine.print_columns(self.hostlist, 4)
+ retention.cliutils.print_columns(self.hostlist, 4)
def dir_completion(self, text, state):
if self.current_dir is None:
- dirs_problem_to_depth = [CommandLine.get_path_prefix(
+ dirs_problem_to_depth = [retention.cliutils.get_path_prefix(
d, self.max_depth_top_level) for d in self.dirs_problem]
dirs_skipped = [s for s in self.dirs_skipped
if s not in dirs_problem_to_depth]
@@ -258,49 +240,6 @@
except IndexError:
return None
- @staticmethod
- def get_path_prefix(path, depth):
- if path is None:
- return path
- if path.count(os.path.sep) < depth:
- return path
- fields = path.split(os.path.sep)
- return os.path.sep.join(fields[:depth + 1])
-
- @staticmethod
- def print_columns(items, cols):
- num_rows = len(items) / cols
- extra = len(items) % cols
- if extra:
- num_rows = num_rows + 1
-
- max_len = {}
- for col in range(0, cols):
- max_len[col] = 0
-
- for row in range(0, num_rows):
- for col in range(0, cols):
- try:
- text = items[row + num_rows * col]
- except IndexError:
- continue
- try:
- count = len(unicode(text, 'utf-8'))
- except:
- count = len(text)
- if len(text) > max_len[col]:
- max_len[col] = len(text)
-
- for row in range(0, num_rows):
- for col in range(0, cols):
- try:
- # fixme ljust probably gets this wrong for
- # text that's really multibyte chars
- print items[row + num_rows * col].ljust(max_len[col]),
- except IndexError:
- pass
- print
-
def do_one_host(self, host, report):
self.set_host(host)
if not retention.utils.running_locally(self.host):
@@ -319,7 +258,7 @@
elif len(self.dirs_problem) == 0 and len(self.dirs_skipped) == 0:
print "No problem dirs and no skipped dirs on this host"
else:
- dirs_problem_to_depth = [CommandLine.get_path_prefix(
+ dirs_problem_to_depth = [retention.cliutils.get_path_prefix(
d, self.max_depth_top_level)
for d in self.dirs_problem]
dirs_skipped = [s for s in self.dirs_skipped
@@ -334,7 +273,7 @@
elif dir_todo not in relevant_dirs:
print "Please choose one of the following directories:"
# fixme another arbitrary setting
- CommandLine.print_columns(relevant_dirs, 5)
+ retention.cliutils.print_columns(relevant_dirs, 5)
else:
self.basedir = None
self.current_dir = None
@@ -442,47 +381,6 @@
command = None
return command
- @staticmethod
- def show_help(level):
- if level == 'status':
- print """Status must be one of the following:
- P (the directory or file may contain sensitive information)
- G (the directory or file is known to be ok and should remain so)
- R (the directory or file is known to be ok but entries
- must be rechecked on next run)
- U (the file or directory has not been checked, status unknown)
- Q (quit this level of the menu)"""
- elif level == 'top':
- print """Command must be one of the following:
- S set the status for the directory
- E examine the directory
- F set filter for listing directory contents
- I ignore this directory or file for now
- R show rules for all dirs/files
- Q quit the menu"""
- elif level == 'examine':
- print """Command must be one of the following:
- D descend the directory tree one level (user will be prompted for
subdir)
- U ascend the directory tree one level (not higher than base of
tree)
- E show information on entries in directory
- F set filter for listing directory contents
- C show first few lines of contents of file in directory
- R show rules covering current directory
- M mark file(s) as ok (user will be prompted for filename expr)
- Q quit the menu"""
- elif level == 'rule':
- print """Command must be one of the following:
- S show all rules for this host
- D show all rules covering the current directory
- C show all rules covering current directory contents
- A add rule to rules store
- R remove rule from rules store
- I import rules from file (overrides dups, won't remove other rules)
- E export rules to file
- Q quit the menu"""
- else:
- print "unknown help level requested,", level
-
def get_dir_contents(self, path, batchno):
# via salt get the directory contents for the first N = 1000
# entries, unsorted.
@@ -517,62 +415,6 @@
fileexamin = RemoteFileExaminer(path, self.host, 20, self.timeout,
quiet=True)
contents = fileexamin.run()
return contents
-
- @staticmethod
- def show_pager(current_page, num_items, num_per_page):
- readline.set_completer(None)
- while True:
- to_show = raw_input("P(prev)/N(next)/F(first)/"
- "L(last)/<num>(go to page num)/Q(quit) [N]: ")
- to_show = to_show.strip()
- if to_show == "":
- to_show = 'N'
-
- if to_show == 'P' or to_show == 'p':
- # prev page
- if current_page > 1:
- return current_page - 1
- else:
- return current_page
-
- elif to_show == 'N' or to_show == 'n':
- # next page
- num_pages = num_items / num_per_page
- if num_items % num_per_page:
- num_pages += 1
- if current_page < num_pages:
- return current_page + 1
- else:
- return current_page
-
- elif to_show == 'F' or to_show == 'f':
- # first page
- return 1
-
- elif to_show == 'L' or 'to_show' == 'l':
- # last page
- num_pages = num_items / num_per_page
- if num_items % num_per_page:
- num_pages += 1
- return num_pages
-
- elif to_show.isdigit():
- desired_page = int(to_show)
- num_pages = num_items / num_per_page
- if num_items % num_per_page:
- num_pages += 1
-
- if desired_page < 1:
- return 1
- elif desired_page > num_pages:
- return num_pages
- else:
- return desired_page
-
- elif to_show == 'Q' or to_show == 'q':
- return None
- else:
- print "unknown option"
def get_basedir_from_path(self, path):
for location in Config.cf[self.locations]:
@@ -694,7 +536,7 @@
if num_pages == 1:
break
- page = CommandLine.show_pager(page, num_items, num_per_page)
+ page = retention.cliutils.show_pager(page, num_items, num_per_page)
if page is None:
return
elif page == num_pages:
@@ -763,13 +605,6 @@
continue
status = Status.text_to_status('good')
retention.ruleutils.do_add_rule(self.cdb, file_expr, filetype,
status, self.host)
- return True
-
- def check_rules_path(self, rules_path):
- # sanity check on the path, let's not read/write
- # into/from anything in the world
-
- # fixme write this
return True
def do_rule(self, command):
@@ -881,7 +716,7 @@
rules_path = rules_path.strip()
if rules_path == '':
return True
- if not self.check_rules_path(rules_path):
+ if not retention.cliutils.check_rules_path(rules_path):
print "bad rules file path specified, aborting"
else:
retention.ruleutils.import_rules(self.cdb, rules_path,
self.host)
@@ -892,7 +727,7 @@
rules_path = rules_path.strip()
if rules_path == '':
return True
- if not self.check_rules_path(rules_path):
+ if not retention.cliutils.check_rules_path(rules_path):
print "bad rules file path specified, aborting"
else:
retention.ruleutils.export_rules(self.cdb, rules_path,
self.host)
@@ -901,7 +736,7 @@
print "quitting this level"
return None
else:
- CommandLine.show_help('rule')
+ retention.cliutils.show_help('rule')
return True
def do_file_contents(self):
@@ -1004,7 +839,7 @@
print "quitting this level"
return None
else:
- CommandLine.show_help('examine')
+ retention.cliutils.show_help('examine')
return True
def do_top(self, command, dir_path):
@@ -1039,7 +874,7 @@
elif command == 'Q' or command == 'q':
return None
else:
- CommandLine.show_help('top')
+ retention.cliutils.show_help('top')
return True
def do_command(self, command, level, dir_path):
@@ -1064,7 +899,7 @@
elif command == 'Q' or command == 'q':
return None
else:
- CommandLine.show_help(level)
+ retention.cliutils.show_help(level)
return True
elif level == 'examine':
return self.do_examine(command)
diff --git a/dataretention/retention/cliutils.py
b/dataretention/retention/cliutils.py
new file mode 100644
index 0000000..3909b02
--- /dev/null
+++ b/dataretention/retention/cliutils.py
@@ -0,0 +1,172 @@
+import os
+import sys
+import readline
+import atexit
+
+sys.path.append('/srv/audits/retention/scripts/')
+
+import retention.remotefileauditor
+import retention.utils
+import retention.fileutils
+import retention.ruleutils
+
+
+def init_readline_hist():
+ readline.parse_and_bind("tab: complete")
+ histfile = os.path.join(os.path.expanduser("~"), ".audit_hist")
+ try:
+ readline.read_history_file(histfile)
+ except IOError:
+ pass
+ atexit.register(readline.write_history_file, histfile)
+ # also fix up delims so we don't have annoying dir elt behavior
+ delims = readline.get_completer_delims()
+ delims = delims.replace("/", "")
+ readline.set_completer_delims(delims)
+
+def save_history(histfile):
+ readline.write_history_file(histfile)
+
+def get_path_prefix(path, depth):
+ if path is None:
+ return path
+ if path.count(os.path.sep) < depth:
+ return path
+ fields = path.split(os.path.sep)
+ return os.path.sep.join(fields[:depth + 1])
+
+def print_columns(items, cols):
+ num_rows = len(items) / cols
+ extra = len(items) % cols
+ if extra:
+ num_rows = num_rows + 1
+
+ max_len = {}
+ for col in range(0, cols):
+ max_len[col] = 0
+
+ for row in range(0, num_rows):
+ for col in range(0, cols):
+ try:
+ text = items[row + num_rows * col]
+ except IndexError:
+ continue
+ try:
+ count = len(unicode(text, 'utf-8'))
+ except:
+ count = len(text)
+ if len(text) > max_len[col]:
+ max_len[col] = len(text)
+
+ for row in range(0, num_rows):
+ for col in range(0, cols):
+ try:
+ # fixme ljust probably gets this wrong for
+ # text that's really multibyte chars
+ print items[row + num_rows * col].ljust(max_len[col]),
+ except IndexError:
+ pass
+ print
+
+def show_help(level):
+ if level == 'status':
+ print """Status must be one of the following:
+ P (the directory or file may contain sensitive information)
+ G (the directory or file is known to be ok and should remain so)
+ R (the directory or file is known to be ok but entries
+ must be rechecked on next run)
+ U (the file or directory has not been checked, status unknown)
+ Q (quit this level of the menu)"""
+ elif level == 'top':
+ print """Command must be one of the following:
+ S set the status for the directory
+ E examine the directory
+ F set filter for listing directory contents
+ I ignore this directory or file for now
+ R show rules for all dirs/files
+ Q quit the menu"""
+ elif level == 'examine':
+ print """Command must be one of the following:
+ D descend the directory tree one level (user will be prompted for
subdir)
+ U ascend the directory tree one level (not higher than base of tree)
+ E show information on entries in directory
+ F set filter for listing directory contents
+ C show first few lines of contents of file in directory
+ R show rules covering current directory
+ M mark file(s) as ok (user will be prompted for filename expr)
+ Q quit the menu"""
+ elif level == 'rule':
+ print """Command must be one of the following:
+ S show all rules for this host
+ D show all rules covering the current directory
+ C show all rules covering current directory contents
+ A add rule to rules store
+ R remove rule from rules store
+ I import rules from file (overrides dups, won't remove other rules)
+ E export rules to file
+ Q quit the menu"""
+ else:
+ print "unknown help level requested,", level
+
+def show_pager(current_page, num_items, num_per_page):
+ readline.set_completer(None)
+ while True:
+ to_show = raw_input("P(prev)/N(next)/F(first)/"
+ "L(last)/<num>(go to page num)/Q(quit) [N]: ")
+ to_show = to_show.strip()
+ if to_show == "":
+ to_show = 'N'
+
+ if to_show == 'P' or to_show == 'p':
+ # prev page
+ if current_page > 1:
+ return current_page - 1
+ else:
+ return current_page
+
+ elif to_show == 'N' or to_show == 'n':
+ # next page
+ num_pages = num_items / num_per_page
+ if num_items % num_per_page:
+ num_pages += 1
+ if current_page < num_pages:
+ return current_page + 1
+ else:
+ return current_page
+
+ elif to_show == 'F' or to_show == 'f':
+ # first page
+ return 1
+
+ elif to_show == 'L' or 'to_show' == 'l':
+ # last page
+ num_pages = num_items / num_per_page
+ if num_items % num_per_page:
+ num_pages += 1
+ return num_pages
+
+ elif to_show.isdigit():
+ desired_page = int(to_show)
+ num_pages = num_items / num_per_page
+ if num_items % num_per_page:
+ num_pages += 1
+
+ if desired_page < 1:
+ return 1
+ elif desired_page > num_pages:
+ return num_pages
+ else:
+ return desired_page
+
+ elif to_show == 'Q' or to_show == 'q':
+ return None
+ else:
+ print "unknown option"
+
+def check_rules_path(rules_path):
+ # sanity check on the path, let's not read/write
+ # into/from anything in the world
+
+ # fixme write this
+ return True
+
--
To view, visit https://gerrit.wikimedia.org/r/233462
To unsubscribe, visit https://gerrit.wikimedia.org/r/settings
Gerrit-MessageType: merged
Gerrit-Change-Id: I3db85c76ea268ff57b77fcff9b3f6873d44dbaab
Gerrit-PatchSet: 2
Gerrit-Project: operations/software
Gerrit-Branch: master
Gerrit-Owner: ArielGlenn <[email protected]>
Gerrit-Reviewer: ArielGlenn <[email protected]>
_______________________________________________
MediaWiki-commits mailing list
[email protected]
https://lists.wikimedia.org/mailman/listinfo/mediawiki-commits