#!/usr/bin/env python3
# coding: UTF-8
"""
Grammalecte builder
"""
import sys
import os
import re
import zipfile
import traceback
import configparser
import datetime
import argparse
import importlib
import unittest
import json
import platform
import shutil
#im2port dialog_bundled
import compile_rules
import helpers
import lex_build
sWarningMessage = "The content of this folder is generated by code and replaced at each build.\n"
def getConfig (sLang):
"load config.ini in <sLang> at gc_lang/<sLang>, returns xConfigParser object"
xConfig = configparser.ConfigParser()
xConfig.optionxform = str
try:
xConfig.read_file(open(f"gc_lang/{sLang}/config.ini", "r", encoding="utf-8"))
except FileNotFoundError:
print(f"# Error. Can’t read config file <{sLang}>")
exit()
return xConfig
def createOptionsLabelProperties (dOptLbl):
"create content for .properties files (LibreOffice)"
sContent = ""
for sOpt, tLabel in dOptLbl.items():
sContent += f"{sOpt}={tLabel[0]}\n"
if tLabel[1]:
sContent += f"hlp_{sOpt}={tLabel[1]}\n"
return sContent
def createDialogOptionsXDL (dVars):
"create bundled dialog options file .xdl (LibreOffice)"
iTab = 1
nPosY = 5
nWidth = 240
sContent = ""
dOpt = dVars["dOptWriter"]
dOptLabel = dVars["dOptLabel"][dVars["lang"]]
for sGroup, lGroupOptions in dVars["lStructOpt"]:
sContent += f'<dlg:fixedline dlg:id="{sGroup}" dlg:tab-index="{iTab}" dlg:top="{nPosY}" dlg:left="5" dlg:width="{nWidth}" dlg:height="10" dlg:value="&{sGroup}" />\n'
iTab += 1
for lLineOptions in lGroupOptions:
nElemWidth = nWidth // len(lLineOptions)
nPosY += 10
nPosX = 10
for sOpt in lLineOptions:
sHelp = f'dlg:help-text="&hlp_{sOpt}"' if dOptLabel[sOpt][1] else ""
sChecked = "true" if dOpt[sOpt] else "false"
sContent += f'<dlg:checkbox dlg:id="{sOpt}" dlg:tab-index="{iTab}" dlg:top="{nPosY}" dlg:left="{nPosX}" dlg:width="{nElemWidth}" dlg:height="10" dlg:value="&{sOpt}" dlg:checked="{sChecked}" {sHelp} />\n'
iTab += 1
nPosX += nElemWidth
nPosY += 10
return sContent
def createOXT (spLang, dVars, dOxt, spLangPack, bInstall):
"create extension for Writer"
print("Building extension for Writer")
spfZip = f"_build/{dVars['name']}-{dVars['lang']}-v{dVars['version']}.oxt"
hZip = zipfile.ZipFile(spfZip, mode='w', compression=zipfile.ZIP_DEFLATED)
# Package and parser
copyGrammalectePyPackageInZipFile(hZip, spLangPack, "pythonpath/")
hZip.write("grammalecte-cli.py", "pythonpath/grammalecte-cli.py")
# Extension files
hZip.writestr("META-INF/manifest.xml", helpers.fileFile("gc_core/py/oxt/manifest.xml", dVars))
hZip.writestr("description.xml", helpers.fileFile("gc_core/py/oxt/description.xml", dVars))
hZip.writestr("Linguistic.xcu", helpers.fileFile("gc_core/py/oxt/Linguistic.xcu", dVars))
hZip.writestr("Grammalecte.py", helpers.fileFile("gc_core/py/oxt/Grammalecte.py", dVars))
hZip.writestr("pythonpath/helpers.py", helpers.fileFile("gc_core/py/oxt/helpers.py", dVars))
for sf in dVars["extras"].split(","):
hZip.writestr(sf.strip(), helpers.fileFile(spLang + '/' + sf.strip(), dVars))
if "logo" in dVars.keys() and dVars["logo"].strip():
hZip.write(spLang + '/' + dVars["logo"].strip(), dVars["logo"].strip())
## OPTIONS
# options dialog within LO/OO options panel (legacy)
#hZip.writestr("pythonpath/lightproof_handler_grammalecte.py", helpers.fileFile("gc_core/py/oxt/lightproof_handler_grammalecte.py", dVars))
#lLineOptions = open(spLang + "/options.txt", "r", encoding="utf-8").readlines()
#dialog_bundled.c(dVars["implname"], lLineOptions, hZip, dVars["lang"])
# options dialog
hZip.writestr("pythonpath/Options.py", helpers.fileFile("gc_core/py/oxt/Options.py", dVars))
hZip.write("gc_core/py/oxt/op_strings.py", "pythonpath/op_strings.py")
# options dialog within Writer options panel
dVars["xdl_dialog_options"] = createDialogOptionsXDL(dVars)
dVars["xcs_options"] = "\n".join([ '<prop oor:name="'+sOpt+'" oor:type="xs:string"><value></value></prop>' for sOpt in dVars["dOptPython"] ])
dVars["xcu_label_values"] = "\n".join([ '<value xml:lang="'+sLang+'">' + dVars["dOptLabel"][sLang]["__optiontitle__"] + '</value>' for sLang in dVars["dOptLabel"] ])
hZip.writestr("dialog/options_page.xdl", helpers.fileFile("gc_core/py/oxt/options_page.xdl", dVars))
hZip.writestr("dialog/OptionsDialog.xcs", helpers.fileFile("gc_core/py/oxt/OptionsDialog.xcs", dVars))
hZip.writestr("dialog/OptionsDialog.xcu", helpers.fileFile("gc_core/py/oxt/OptionsDialog.xcu", dVars))
hZip.writestr("dialog/" + dVars['lang'] + "_en.default", "")
for sLangLbl, dOptLbl in dVars['dOptLabel'].items():
hZip.writestr(f"dialog/{dVars['lang']}_{sLangLbl}.properties", createOptionsLabelProperties(dOptLbl))
## ADDONS OXT
print("+ OXT: ", end="")
for spfSrc, spfDst in dOxt.items():
print(spfSrc, end=", ")
if os.path.isdir(spLang+'/'+spfSrc):
for sf in os.listdir(spLang+'/'+spfSrc):
if sf.endswith(('.txt', '.py')):
hZip.writestr(spfDst+"/"+sf, helpers.fileFile(spLang+'/'+spfSrc+"/"+sf, dVars))
else:
hZip.write(spLang+'/'+spfSrc+"/"+sf, spfDst+"/"+sf)
else:
if spfSrc.endswith(('.txt', '.py')):
hZip.writestr(spfDst, helpers.fileFile(spLang+'/'+spfSrc, dVars))
else:
hZip.write(spLang+'/'+spfSrc, spfDst)
print()
hZip.close()
# Installation in Writer profile
if bInstall:
print("> installation in Writer")
if dVars.get('unopkg', False):
cmd = '"'+os.path.abspath(dVars.get('unopkg')+'" add -f '+spfZip)
print(cmd)
os.system(cmd)
else:
print("# Error: path and filename of unopkg not set in config.ini")
def createPackageZip (dVars, spLangPack):
"create server zip"
spfZip = f"_build/{dVars['name']}-{dVars['lang']}-v{dVars['version']}.zip"
hZip = zipfile.ZipFile(spfZip, mode='w', compression=zipfile.ZIP_DEFLATED)
copyGrammalectePyPackageInZipFile(hZip, spLangPack)
for spf in ["grammalecte-cli.py", "grammalecte-server.py", \
"README.txt", "LICENSE.txt", "LICENSE.fr.txt"]:
hZip.write(spf)
helpers.addFileToZipAndFileFile(hZip, "dockerfile.txt", "Dockerfile", dVars)
helpers.addFileToZipAndFileFile(hZip, "gc_lang/fr/setup.py", "setup.py", dVars)
#hZip.writestr("setup.py", helpers.fileFile("gc_lang/fr/setup.py", dVars))
def copyGrammalectePyPackageInZipFile (hZip, spLangPack, sAddPath=""):
"copy Grammalecte Python package in zip file"
for sf in os.listdir("grammalecte"):
if not os.path.isdir("grammalecte/"+sf):
hZip.write("grammalecte/"+sf, sAddPath+"grammalecte/"+sf)
for sf in os.listdir("grammalecte/graphspell"):
if not os.path.isdir("grammalecte/graphspell/"+sf):
hZip.write("grammalecte/graphspell/"+sf, sAddPath+"grammalecte/graphspell/"+sf)
for sf in os.listdir("grammalecte/graphspell/_dictionaries"):
if not os.path.isdir("grammalecte/graphspell/_dictionaries/"+sf):
hZip.write("grammalecte/graphspell/_dictionaries/"+sf, sAddPath+"grammalecte/graphspell/_dictionaries/"+sf)
for sf in os.listdir(spLangPack):
if not os.path.isdir(spLangPack+"/"+sf):
hZip.write(spLangPack+"/"+sf, sAddPath+spLangPack+"/"+sf)
def create (sLang, xConfig, bInstallOXT, bJavaScript, bUseCache):
"make Grammalecte for project <sLang>"
print(f">>>> MAKE GC ENGINE: {sLang} <<<<")
#### READ CONFIGURATION
print("> read configuration...")
spLang = "gc_lang/" + sLang
dVars = xConfig._sections['args']
dVars['locales'] = dVars["locales"].replace("_", "-")
dVars['loc'] = str({ s: [s[0:2], s[3:5], ""] for s in dVars["locales"].split(" ") })
## COMPILE RULES
dResult = compile_rules.make(spLang, dVars['lang'], bUseCache)
dVars.update(dResult)
## READ GRAMMAR CHECKER PLUGINS
print("PYTHON:")
print("+ Plugins: ", end="")
sCodePlugins = ""
for sf in os.listdir(spLang+"/modules"):
if re.match(r"gce_\w+[.]py$", sf):
sCodePlugins += "\n\n" + open(spLang+'/modules/'+sf, "r", encoding="utf-8").read()
print(sf, end=", ")
print()
dVars["plugins"] = sCodePlugins
## COPY GC_CORE COMMON FILES
for sf in os.listdir("gc_core/py"):
if not os.path.isdir("gc_core/py/"+sf):
helpers.copyAndFileTemplate("gc_core/py/"+sf, "grammalecte/"+sf, dVars)
shutil.copy2("3rd/bottle.py", "grammalecte/bottle.py")
open("grammalecte/WARNING.txt", "w", encoding="utf-8", newline="\n").write(sWarningMessage)
## CREATE GRAMMAR CHECKER PACKAGE
spLangPack = "grammalecte/"+sLang
helpers.createCleanFolder(spLangPack)
for sf in os.listdir("gc_core/py/lang_core"):
if not os.path.isdir("gc_core/py/lang_core/"+sf):
helpers.copyAndFileTemplate("gc_core/py/lang_core/"+sf, spLangPack+"/"+sf, dVars)
print("+ Modules: ", end="")
for sf in os.listdir(spLang+"/modules"):
if not sf.startswith(("gce_", "__pycache__")):
helpers.copyAndFileTemplate(spLang+"/modules/"+sf, spLangPack+"/"+sf, dVars)
print(sf, end=", ")
print()
# TEST FILES
with open("grammalecte/"+sLang+"/gc_test.txt", "w", encoding="utf-8", newline="\n") as hDstPy:
hDstPy.write("# TESTS FOR LANG [" + sLang + "]\n\n")
hDstPy.write(dVars['gctests'])
hDstPy.write("\n")
createOXT(spLang, dVars, xConfig._sections['oxt'], spLangPack, bInstallOXT)
createPackageZip(dVars, spLangPack)
#### JAVASCRIPT
if bJavaScript:
print("JAVASCRIPT:")
print("+ Plugins: ", end="")
sCodePlugins = ""
for sf in os.listdir(spLang+"/modules-js"):
if re.match(r"gce_\w+[.]js$", sf):
sCodePlugins += "\n\n" + open(spLang+'/modules-js/'+sf, "r", encoding="utf-8").read()
print(sf, end=", ")
print()
dVars["pluginsJS"] = sCodePlugins
# options data struct
dVars["dOptJavaScript"] = json.dumps(list(dVars["dOptJavaScript"].items()))
dVars["dOptFirefox"] = json.dumps(list(dVars["dOptFirefox"].items()))
dVars["dOptThunderbird"] = json.dumps(list(dVars["dOptThunderbird"].items()))
# create folder
spLangPack = "grammalecte-js/"+sLang
helpers.createCleanFolder(spLangPack)
# create files
for sf in os.listdir("js_extension"):
dVars[sf[:-3]] = open("js_extension/"+sf, "r", encoding="utf-8").read()
for sf in os.listdir("gc_core/js"):
if not os.path.isdir("gc_core/js/"+sf) and not sf.startswith("jsex_"):
helpers.copyAndFileTemplate("gc_core/js/"+sf, "grammalecte-js/"+sf, dVars)
open("grammalecte-js/WARNING.txt", "w", encoding="utf-8", newline="\n").write(sWarningMessage)
for sf in os.listdir("gc_core/js/lang_core"):
if not os.path.isdir("gc_core/js/lang_core/"+sf) and sf.startswith("gc_"):
helpers.copyAndFileTemplate("gc_core/js/lang_core/"+sf, spLangPack+"/"+sf, dVars)
print("+ Modules: ", end="")
for sf in os.listdir(spLang+"/modules-js"):
if not sf.startswith("gce_"):
helpers.copyAndFileTemplate(spLang+"/modules-js/"+sf, spLangPack+"/"+sf, dVars)
print(sf, end=", ")
print()
try:
buildjs = importlib.import_module("gc_lang."+sLang+".build")
except ImportError:
print("# No complementary builder <build.py> in folder gc_lang/"+sLang)
else:
buildjs.build(sLang, dVars)
return dVars['version']
def copyGraphspellCore (bJavaScript=False):
"copy Graphspell package in Grammalecte package"
print("> Copy Graphspell package in Grammalecte package")
helpers.createCleanFolder("grammalecte/graphspell")
os.makedirs("grammalecte/graphspell/_dictionaries", exist_ok=True)
for sf in os.listdir("graphspell"):
if not os.path.isdir("graphspell/"+sf):
shutil.copy2("graphspell/"+sf, "grammalecte/graphspell")
if bJavaScript:
helpers.createCleanFolder("grammalecte-js/graphspell")
os.makedirs("grammalecte-js/graphspell/_dictionaries", exist_ok=True)
dVars = {}
for sf in os.listdir("js_extension"):
dVars[sf[:-3]] = open("js_extension/"+sf, "r", encoding="utf-8").read()
for sf in os.listdir("graphspell-js"):
if not os.path.isdir("graphspell-js/"+sf):
shutil.copy2("graphspell-js/"+sf, "grammalecte-js/graphspell")
helpers.copyAndFileTemplate("graphspell-js/"+sf, "grammalecte-js/graphspell/"+sf, dVars)
def copyGraphspellDictionaries (dVars, bJavaScript=False, bCommunityDict=False, bPersonalDict=False):
"copy requested Graphspell dictionaries in Grammalecte package"
print("> Copy requested Graphspell dictionaries in Grammalecte package")
dVars["dic_main_filename_py"] = ""
dVars["dic_main_filename_js"] = ""
dVars["dic_community_filename_py"] = ""
dVars["dic_community_filename_js"] = ""
dVars["dic_personal_filename_py"] = ""
dVars["dic_personal_filename_js"] = ""
lDict = [ ("main", s) for s in dVars['dic_filenames'].split(",") ]
if bCommunityDict:
lDict.append(("community", dVars['dic_community_filename']))
if bPersonalDict:
lDict.append(("personal", dVars['dic_personal_filename']))
for sType, sFileName in lDict:
spfPyDic = f"graphspell/_dictionaries/{sFileName}.json"
spfJSDic = f"graphspell-js/_dictionaries/{sFileName}.json"
if not os.path.isfile(spfPyDic) or (bJavaScript and not os.path.isfile(spfJSDic)):
buildDictionary(dVars, sType, bJavaScript)
print(" +", spfPyDic)
shutil.copy2(spfPyDic, "grammalecte/graphspell/_dictionaries")
dVars['dic_'+sType+'_filename_py'] = sFileName + '.json'
if bJavaScript:
print(" +", spfJSDic)
shutil.copy2(spfJSDic, "grammalecte-js/graphspell/_dictionaries")
dVars['dic_'+sType+'_filename_js'] = sFileName + '.json'
dVars['dic_main_filename_py'] = dVars['dic_default_filename_py'] + ".json"
dVars['dic_main_filename_js'] = dVars['dic_default_filename_js'] + ".json"
def buildDictionary (dVars, sType, bJavaScript=False):
"build binary dictionary for Graphspell from lexicons"
if sType == "main":
spfLexSrc = dVars['lexicon_src']
lSfDictDst = dVars['dic_filenames'].split(",")
lDicName = dVars['dic_name'].split(",")
lDescription = dVars['dic_description'].split(",")
lFilter = dVars['dic_filter'].split(",")
for sfDictDst, sDicName, sDescription, sFilter in zip(lSfDictDst, lDicName, lDescription, lFilter):
lex_build.build(spfLexSrc, dVars['lang'], dVars['lang_name'], sfDictDst, bJavaScript, sDicName, sDescription, sFilter, dVars['stemming_method'], int(dVars['fsa_method']))
else:
if sType == "community":
spfLexSrc = dVars['lexicon_community_src']
sfDictDst = dVars['dic_community_filename']
sDicName = dVars['dic_community_name']
sDescription = dVars['dic_community_description']
elif sType == "personal":
spfLexSrc = dVars['lexicon_personal_src']
sfDictDst = dVars['dic_personal_filename']
sDicName = dVars['dic_personal_name']
sDescription = dVars['dic_personal_description']
lex_build.build(spfLexSrc, dVars['lang'], dVars['lang_name'], sfDictDst, bJavaScript, sDicName, sDescription, "", dVars['stemming_method'], int(dVars['fsa_method']))
def extraTest (sLang):
"test grammar checker with files in <gc_lang/xx/tests>"
if os.path.isdir(f"gc_lang/{sLang}/tests"):
print(f">>>>>>>>>> EXTRA TESTS: parsing texts in <gc_lang/{sLang}/tests>\n")
grammalecte = importlib.import_module("grammalecte")
oGrammarChecker = grammalecte.GrammarChecker(sLang)
for sf in os.listdir(f"gc_lang/{sLang}/tests"):
if sf.startswith("test_") and sf.endswith(".txt"):
spf = f"gc_lang/{sLang}/tests/" + sf
with open(spf, "r", encoding="utf-8") as hSrc:
print(f"\n>>>>>>>>>> TEST TEXT: {spf} <<<<<<<<<<\n")
nLine = sum(1 for _ in hSrc)
nPercent = max(nLine // 100, 1)
hSrc.seek(0) # rewind to the beginning of the file
nTotError = 0
for i, sLine in enumerate(hSrc, 1):
if (i % nPercent == 0):
print(f"\r> Test text: {spf} ({i // nPercent} %)", end="")
aGrammErrs, aSpellErrs = oGrammarChecker.getParagraphErrors(sLine)
if aGrammErrs:
sText, _ = grammalecte.text.generateParagraph(sLine, aGrammErrs, aSpellErrs, 160)
print(f"\n# Line {i}")
print(sText)
nTotError += 1
print(f"\r> Test text: {spf} ({i // nPercent} %): {i} lines. Grammar errors in {nTotError} lines.")
else:
print(f"# Error. No folder <gc_lang/{sLang}/tests>. With option -tt, all texts named <test_*.txt> in this folder will be parsed by the grammar checker.")
def main ():
"build Grammalecte with requested options"
print("Python: " + sys.version)
if sys.version_info < (3, 7):
print("Python 3.7+ required")
return
xParser = argparse.ArgumentParser()
xParser.add_argument("lang", type=str, nargs='+', help="lang project to generate (name of folder in /lang)")
xParser.add_argument("-uc", "--use_cache", help="use data cache instead of rebuilding rules", action="store_true")
xParser.add_argument("-frb", "--force_rebuild", help="force rebuilding rules", action="store_true")
xParser.add_argument("-b", "--build_data", help="launch build_data.py (part 1 and 2)", action="store_true")
xParser.add_argument("-bb", "--build_data_before", help="launch build_data.py (only part 1: before dictionary building)", action="store_true")
xParser.add_argument("-ba", "--build_data_after", help="launch build_data.py (only part 2: after dictionary building)", action="store_true")
xParser.add_argument("-d", "--dict", help="generate FSA dictionary", action="store_true")
xParser.add_argument("-t", "--tests", help="run unit tests", action="store_true")
xParser.add_argument("-tt", "--test_texts", help="perform gc tests on texts", action="store_true")
xParser.add_argument("-p", "--perf", help="run performance tests", action="store_true")
xParser.add_argument("-pm", "--perf_memo", help="run performance tests and store results in perf_memo.txt", action="store_true")
xParser.add_argument("-js", "--javascript", help="JavaScript build for Firefox", action="store_true")
xParser.add_argument("-acd", "--add_community_dictionary", help="add community dictionary to the build", action="store_true")
xParser.add_argument("-apd", "--add_personal_dictionary", help="add personal dictionary to the build", action="store_true")
xParser.add_argument("-fx", "--firefox", help="Launch Firefox for WebExtension testing", action="store_true")
xParser.add_argument("-fxd", "--firefox_dev", help="Launch Firefox Developper for WebExtension testing", action="store_true")
xParser.add_argument("-fxn", "--firefox_nightly", help="Launch Firefox Nightly for WebExtension testing", action="store_true")
xParser.add_argument("-l", "--lint_web_ext", help="web-ext lint on the WebExtension", action="store_true")
xParser.add_argument("-tb", "--thunderbird", help="Launch Thunderbird", action="store_true")
xParser.add_argument("-tbb", "--thunderbird_beta", help="Launch Thunderbird Beta", action="store_true")
xParser.add_argument("-i", "--install", help="install the extension in Writer (path of unopkg must be set in config.ini)", action="store_true")
xArgs = xParser.parse_args()
oNow = datetime.datetime.now()
print("============== MAKE GRAMMALECTE at {0.hour:>2} h {0.minute:>2} min {0.second:>2} s ==============".format(oNow))
if xArgs.build_data:
xArgs.build_data_before = True
xArgs.build_data_after = True
os.makedirs("_build", exist_ok=True)
os.makedirs("grammalecte", exist_ok=True)
if xArgs.javascript:
os.makedirs("grammalecte-js", exist_ok=True)
copyGraphspellCore(xArgs.javascript)
for sLang in xArgs.lang:
if os.path.exists("gc_lang/"+sLang) and os.path.isdir("gc_lang/"+sLang):
xConfig = getConfig(sLang)
dVars = xConfig._sections['args']
if not dVars["lexicon_community_src"]:
xArgs.add_community_dictionary = False
if not dVars["lexicon_personal_src"]:
xArgs.add_personal_dictionary = False
# build data
databuild = None
if xArgs.build_data_before or xArgs.build_data_after:
# lang data
try:
databuild = importlib.import_module("gc_lang."+sLang+".build_data")
except ImportError:
print("# Error. Couldn’t import file build_data.py in folder gc_lang/"+sLang)
if databuild and xArgs.build_data_before:
databuild.before('gc_lang/'+sLang, dVars, xArgs.javascript)
if xArgs.dict:
buildDictionary(dVars, "main", xArgs.javascript)
if xArgs.add_community_dictionary:
buildDictionary(dVars, "community", xArgs.javascript)
if xArgs.add_personal_dictionary:
buildDictionary(dVars, "personal", xArgs.javascript)
if databuild and xArgs.build_data_after:
databuild.after('gc_lang/'+sLang, dVars, xArgs.javascript)
# copy dictionaries from Graphspell
copyGraphspellDictionaries(dVars, xArgs.javascript, xArgs.add_community_dictionary, xArgs.add_personal_dictionary)
# make
bUseCache = None # we may rebuild if it’s necessary
if xArgs.use_cache:
bUseCache = True # we use the cache if it exists
if xArgs.force_rebuild:
bUseCache = False # we rebuild
sVersion = create(sLang, xConfig, xArgs.install, xArgs.javascript, bUseCache)
# Tests
if xArgs.tests:
print("> Running tests")
lTestModules = [f"grammalecte.{sLang}.tests_core", \
f"grammalecte.{sLang}.tests_modules"]
xTestSuite = unittest.TestLoader().loadTestsFromNames(lTestModules)
unittest.TextTestRunner().run(xTestSuite)
if xArgs.perf or xArgs.perf_memo:
try:
tests = importlib.import_module(f"grammalecte.{sLang}.tests_core")
except ImportError:
print(f"# Error. Import failed: grammalecte.{sLang}.tests_core")
else:
sResultFile = f"gc_lang/{sLang}/perf_memo.txt" if xArgs.perf_memo else ""
tests.perf(sVersion, sResultFile)
if xArgs.test_texts:
extraTest(sLang)
# JavaScript linter
if xArgs.lint_web_ext:
with helpers.CD("_build/webext/"+sLang):
os.system(r'web-ext lint -o text')
# Firefox
if xArgs.firefox: # Firefox
with helpers.CD("_build/webext/"+sLang):
spfFirefox = dVars['win_fx_path'] if platform.system() == "Windows" else dVars['linux_fx_path']
os.system(r'web-ext run --firefox="' + spfFirefox + '" --browser-console')
if xArgs.firefox_dev: # Firefox Developer edition
with helpers.CD("_build/webext/"+sLang):
spfFirefox = dVars['win_fx_dev_path'] if platform.system() == "Windows" else dVars['linux_fx_dev_path']
os.system(r'web-ext run --firefox="' + spfFirefox + '" --browser-console')
if xArgs.firefox_nightly: # Firefox Nightly edition
with helpers.CD("_build/webext/"+sLang):
spfFirefox = dVars['win_fx_nightly_path'] if platform.system() == "Windows" else dVars['linux_fx_nightly_path']
os.system(r'web-ext run --firefox="' + spfFirefox + '" --browser-console')
# https://github.com/mozilla/web-ext/issues/932
# os.system(r'web-ext run --firefox="' + spfFirefox + r'" --browser-console --firefox-profile=C:\Users\EAK\AppData\Roaming\Mozilla\Firefox\Profiles\e26559tw.debug --keep-profile-changes')
# Thunderbird
if xArgs.thunderbird:
spfThunderbird = '"'+dVars['win_tb_path']+'"' if platform.system() == "Windows" else dVars['linux_tb_path']
print(spfThunderbird)
os.system(spfThunderbird + ' -jsconsole -P debug')
if xArgs.thunderbird_beta:
spfThunderbird = '"'+dVars['win_tb_beta_path']+'"' if platform.system() == "Windows" else dVars['linux_tb_beta_path']
print(spfThunderbird)
os.system(spfThunderbird + ' -jsconsole -P beta')
else:
print("Folder not found: gc_lang/"+sLang)
oNow = datetime.datetime.now()
print("============== MAKE GRAMMALECTE [finished] at {0.hour:>2} h {0.minute:>2} min {0.second:>2} s ==============".format(oNow))
if __name__ == '__main__':
main()