#!/usr/bin/env python # # Copyright 2004-2006 Zuza Software Foundation # # This file is part of translate. # # translate is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # translate 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 General Public License for more details. # # You should have received a copy of the GNU General Public License # along with translate; if not, write to the Free Software # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA from Pootle import pootlefile from Pootle import projects from Pootle import potree from Pootle import pootle from Pootle import users from translate.storage import po from translate.search import indexing import os import profile import pstats class PootleBenchmarker: """class to aid in benchmarking pootle""" StoreClass = pootlefile.pootlefile UnitClass = pootlefile.pootleunit def __init__(self, test_dir): """sets up benchmarking on the test directory""" self.test_dir = os.path.abspath(test_dir) self.project_dir = os.path.join(self.test_dir, "benchmark") self.po_dir = os.path.join(self.project_dir, "zxx") def clear_test_dir(self): """removes the given directory""" if os.path.exists(self.test_dir): for dirpath, subdirs, filenames in os.walk(self.test_dir, topdown=False): for name in filenames: os.remove(os.path.join(dirpath, name)) for name in subdirs: os.rmdir(os.path.join(dirpath, name)) if os.path.exists(self.test_dir): os.rmdir(self.test_dir) assert not os.path.exists(self.test_dir) def setup_server(self): """gets a pootle server""" cwd = os.path.abspath(os.path.curdir) parser = pootle.PootleOptionParser() prefsfile = os.path.join(self.test_dir, "pootle.prefs") pootleprefsstr = """ importmodules.pootleserver = 'Pootle.pootle' Pootle: serverclass = pootleserver.PootleServer sessionkey = 'dummy' baseurl = "/" userprefs = "users.prefs" podirectory = "%s" projects.benchmark: fullname = "Benchmark" description = "Benchmark auto-created files" checkstyle = "standard" localfiletype = "po" languages.zxx.fullname = "Test Language" """ % (self.test_dir) open(prefsfile, "w").write(pootleprefsstr) userprefsfile = os.path.join(self.test_dir, "users.prefs") open(userprefsfile, "w").write("testuser.activated=1\ntestuser.passwdhash = 'dd82c1882969461de74b46427961ea2c'\n") options, args = parser.parse_args(["--prefsfile=%s" % prefsfile]) options.servertype = "dummy" self.server = parser.getserver(options) os.chdir(cwd) return self.server def get_session(self): """gets a new session object""" return users.PootleSession(self.server.sessioncache, self.server) def create_sample_files(self, num_dirs, files_per_dir, strings_per_file, source_words_per_string, target_words_per_string): """creates sample files for benchmarking""" if not os.path.exists(self.test_dir): os.mkdir(self.test_dir) if not os.path.exists(self.project_dir): os.mkdir(self.project_dir) if not os.path.exists(self.po_dir): os.mkdir(self.po_dir) for dirnum in range(num_dirs): if num_dirs > 1: dirname = os.path.join(self.po_dir, "sample_%d" % dirnum) if not os.path.exists(dirname): os.mkdir(dirname) else: dirname = self.po_dir for filenum in range(files_per_dir): sample_file = self.StoreClass(pofilename=os.path.join(dirname, "file_%d.po" % filenum)) for stringnum in range(strings_per_file): source_string = " ".join(["word%d" % i for i in range(source_words_per_string)]) sample_unit = sample_file.addsourceunit(source_string) sample_unit.target = " ".join(["drow%d" % i for i in range(target_words_per_string)]) sample_file.savepofile() def parse_po_files(self): """parses all the po files in the test directory into memory""" count = 0 for dirpath, subdirs, filenames in os.walk(self.po_dir, topdown=False): for name in filenames: pofilename = os.path.join(dirpath, name) parsedfile = po.pofile(open(pofilename, 'r')) count += len(parsedfile.units) print "counted %d units" % count def parse_and_create_stats(self): """parses all the po files in the test directory into memory, using pootlefile, which creates Stats""" count = 0 indexing.HAVE_INDEXER = False for dirpath, subdirs, filenames in os.walk(self.po_dir, topdown=False): for name in filenames: pofilename = os.path.join(dirpath, name) parsedfile = pootlefile.pootlefile(pofilename=pofilename) count += len(parsedfile.units) print "stats on %d units" % count def parse_and_create_index(self): """parses all the po files in the test directory into memory, using pootlefile, and allow index creation""" count = 0 indexing.HAVE_INDEXER = True self.server.potree.projectcache.clear() project = self.server.potree.getproject("zxx", "benchmark") for name in project.browsefiles(): count += len(project.getpofile(name).units) print "indexed %d units" % count assert os.path.exists(os.path.join(self.po_dir, ".poindex-%s-%s" % (project.projectcode, project.languagecode))) def generate_main_page(self): """tests generating the main page""" session = self.get_session() page = self.server.getpage(["index.html"], session, {}) print page.templatevars def generate_projectindex_page(self): """tests generating the index page for the project""" session = self.get_session() assert self.server.potree.haslanguage("zxx") assert self.server.potree.hasproject("zxx", "benchmark") page = self.server.getpage(["zxx", "benchmark"], session, {}) print page.templatevars def generate_translation_page(self): """tests generating the translation page for the file""" session = self.get_session() page = self.server.getpage(["zxx", "benchmark", "translate.html"], session, {}) print page.templatevars def submit_translation_change(self): """tests generating the translation page for the file""" session = self.get_session() project = self.server.potree.getproject("zxx", "benchmark") project.setrights(None, ["view", "translate"]) pofilename = project.browsefiles()[0] args = {"pofilename": pofilename, "submit0": "true", "trans0": "changed"} page = self.server.getpage(["zxx", "benchmark", "translate.html"], session, args) pofile = project.getpofile(pofilename) print str(pofile.getitem(0)) # assert fails because of multistring # assert pofile.getitem(0).unquotedmsgstr == "changed" print page.templatevars if __name__ == "__main__": for sample_file_sizes in [ # num_dirs, files_per_dir, strings_per_file, source_words_per_string, target_words_per_string # (1, 1, 1, 1, 1), (1, 1, 30, 10, 10), # (1, 5, 10, 10, 10), (1, 10, 10, 10, 10), (5, 10, 10, 10, 10), # (5, 10, 100, 20, 20), # (10, 20, 100, 10, 10), ]: benchmarker = PootleBenchmarker("BenchmarkDir") benchmarker.clear_test_dir() benchmarker.create_sample_files(*sample_file_sizes) benchmarker.setup_server() methods = ["parse_po_files", "parse_and_create_stats", "parse_and_create_index", "generate_main_page", "generate_projectindex_page", "generate_translation_page", "submit_translation_change", ] for methodname in methods: print methodname, "%d dirs, %d files, %d strings, %d/%d words" % sample_file_sizes print "_______________________________________________________" statsfile = methodname + '_%d_%d_%d_%d_%d.stats' % sample_file_sizes profile.run('benchmarker.%s()' % methodname, statsfile) stats = pstats.Stats(statsfile) stats.sort_stats('cumulative').print_stats(20) print "_______________________________________________________" benchmarker.clear_test_dir()