#!/usr/bin/python
import os, sys, re, base64
def generate():
sections = {}
exclude_sections = []
replacements = {}
for keyword, prompt_text in repl_vars:
replacements[keyword] = prompt(prompt_text)
answer = ''
while not answer.lower() in ['f', 't']:
answer = prompt('Firefox or Thunderbird (f/t) ')
sections['firefox'] = answer.lower() == 'f'
sections['thunderbird'] = answer.lower() == 't'
for keyword, prompt_text in section_vars:
answer = ''
while not answer.lower() in ['y', 'n']:
answer = prompt('Include %s ? (y/n)' % prompt_text)
sections[keyword] = answer.lower() == 'y'
if sections['menuitem']:
replacements['menuName'] = prompt('Menu item label')
replacements['menuAccessKey'] = prompt('Menu item access key')
if sections['contextmenu']:
replacements['contextName'] = prompt('Contextmenu item label')
replacements['contextAccessKey'] = prompt('Contextmenu item access key')
extname = replacements['name'].lower()
replacements['lname'] = extname
replacements['llib'] = replacements['lib'].lower()
#Make all dirs needed
os.makedirs(extname)
for d in dirs:
os.makedirs(os.path.join(extname, d))
#Process library file specially
libfile = open('mozlib/mozlib.js', 'r')
libtext = libfile.read()
libfile.close()
libfileout = open(os.path.join(extname, 'chrome/content', replacements['llib']) + '.js', 'w')
libfileout.write(libtext.replace('MozLib', replacements['lib']))
libfileout.flush()
libfileout.close()
#Proccess each file
for filename, filecontent in files:
is_img = filename[-3:] == 'png'
print filename
#Include or exclude sections of code
exclude_pattern = r'\[%s].*?\[/%s]\s*\n'
include_pattern = r'\[/?%s]\s*\n'
for key in sections:
if sections[key]:
pattern = include_pattern % key
else:
pattern = exclude_pattern % (key, key)
regex = re.compile(pattern, re.DOTALL)
filecontent = re.sub(regex, '', filecontent)
#Simple keyword replacements
filename = filename % replacements
if not is_img:
filecontent = filecontent % replacements
filecontent = filecontent.strip()
#The whole file might be wrapped in a section, and if the section
#was removed we don't want to create the file
if filecontent:
if is_img:
filecontent = base64.b64decode(filecontent)
path = extname + '/' + filename
file = open(path, 'wb')
file.write(filecontent)
file.flush()
file.close()
def prompt(prompt_text):
sys.stdout.write(prompt_text + ': ')
return raw_input()
#Directories to create
dirs = ['chrome/content', 'chrome/locale/en-US', 'chrome/skin', 'defaults/preferences']
repl_vars = (
('prettyname', 'Extension name'),
('name', 'Extension code name'),
('descr', 'Extension description'),
('lib', 'Library name'),
)
section_vars = (
('options', 'Options dialog'),
('menuitem', 'Menu item'),
('contextmenu', 'Context menu'),
)
#Below here are only file templates
files = (
('install.rdf',
"""
%(lname)s@einaregilsson.com
%(prettyname)s
0.1
Einar Egilsson
%(descr)s
chrome://%(lname)s/content/about.xul
chrome://%(lname)s/content/options.xul
chrome://%(lname)s/content/%(lname)s.png
[firefox]
{ec8030f7-c20a-464f-9b0e-13a3a9e97384}
2.0
2.0.0.*
[/firefox]
[thunderbird]
{3550f703-e582-4d05-9a08-453d09bdfdc6}
1.5
1.5.0.*
[/thunderbird]
"""),
('chrome.manifest',
"""
# $Id$
content %(lname)s file:chrome/content/
locale %(lname)s en-US file:chrome/locale/en-US/
skin %(lname)s classic/1.0 file:chrome/skin/
[thunderbird]
overlay chrome://messenger/content/messenger.xul chrome://%(lname)s/content/overlay.xul
[/thunderbird]
[firefox]
overlay chrome://browser/content/browser.xul chrome://%(lname)s/content/overlay.xul
[/firefox]
"""),
('make.bat',
"""
::
:: Build script for extension
::
:: Einar Thor Egilsson - 26.10.2006
::
:: $Id$
SET EXT=%(name)s.xpi
IF NOT EXIST build md build
IF EXIST build\%%EXT%% del build\%%EXT%%
zip -r build\%%EXT%% *.* -x build* *.py *.bat
"""),
('defaults/preferences/%(lname)s.js',
"""
//// $Id$
pref("extensions.%(lname)s.debug", false);
// See http://kb.mozillazine.org/Localize_extension_descriptions
pref("extensions.%(lname)s@einaregilsson.com.description", "chrome://%(lname)s/locale/%(lname)s.properties");
"""),
('chrome/content/%(lname)s.js',
"""
//// $Id$
var %(name)s = {
id : "%(lname)s@einaregilsson.com",
name : "%(name)s",
initialized : false,
strings : null,
onLoad : function(event) {
try {
// initialization code
%(lib)s.initialize(this);
[contextmenu]
[thunderbird]
$('threadPaneContext')
[/thunderbird]
[firefox]
$('contentAreaContextMenu')
[/firefox]
.addEventListener("popupshowing", function(e) { %(name)s.showContextMenu(e); }, false);
[/contextmenu]
%(lib)s.debug("Initializing...");
this.strings = document.getElementById("%(lname)s-strings");
%(lib)s.debug("Finished initialization");
this.initialized = true;
} catch(e) {
//Don't use %(lib)s because it's initialization might have failed.
if (this.strings) {
alert(this.strings.getString("initError")._(this.name) + "\\n\\n" + e);
} else {
alert(e);
}
}
},
onUnload : function(event) {
//Clean up here
%(lib)s.debug("Finished cleanup");
},
[contextmenu]
showContextMenu : function(event) {
[thunderbird]
$("%(lname)s-context").hidden = (GetNumSelectedMessages() > 0);
[/thunderbird]
[firefox]
$("%(lname)s-context").hidden = gContextMenu.onImage;
[/firefox]
},
onContextMenuCommand: function(event) {
//Do your thing
alert("Context menu command");
},
[/contextmenu]
[menuitem]
onMenuItemCommand: function(event) {
alert("Menu item command");
[options]
window.open("chrome://%(lname)s/content/options.xul",
"settings",
"chrome,dialog,modal,centerscreen");
[/options]
},
[/menuitem]
};
window.addEventListener("load", function(event) { %(name)s.onLoad(event); }, false);
window.addEventListener("unload", function(event) { %(name)s.onUnload(event); }, false);
"""),
('chrome/content/overlay.xul',
"""
[firefox]
[menuitem]
[/menuitem]
[contextmenu]
[/contextmenu]
[/firefox]
[thunderbird]
[menuitem]
[/menuitem]
[contextmenu]
[/contextmenu]
[/thunderbird]
"""),
('chrome/skin/overlay.css',
"""
/* $Id$ */
/* Include your overlay stylings here */
"""),
('chrome/content/%(lname)s.png',
"""
iVBORw0KGgoAAAANSUhEUgAAACIAAAAiCAIAAAC1JZyVAAAACXBIWXMAAAsTAAALEwEAmpwYAAAABGdB
TUEAALGOfPtRkwAAACBjSFJNAAB6JQAAgIMAAPn/AACA6QAAdTAAAOpgAAA6mAAAF2+SX8VGAAAFLElE
QVR42oSGgQ0AIAzCRAb/nyzjAduEgvMDAO8FOSxT06BaJO14vDeRE2eWJ4BYCNsBtIQJaC4T1GiYFRCz
gTyQKWCjwBTQZLB1rGALwPYA2QABhM8aoB+YgA4H2gL2CtBYJpgNzCxgX8B8AzYRZBGIgNkAhWC7AAKI
BbcdTGAfgL3CAg0xsPtZmFmZoWEFCh0WqFdYoeGD5AWwPWAeQABht4YZbDwz1BvMKAHFArUBEkaoABFi
IDvZ2dlgogABhG4NI8QfIAgKL1hkg0iYD+DRDYkTFhawmWzQYALZghJeYB5AALGgRTg4rJiZmOGhBKJZ
YZHBDLMAbCfYUBZ4cmKDxzvQF2DbwL5hB0kDBBALasJlZmKBeoQFmnQxA4oFEtMw30CcCzGXDe4Ldnhy
BomxAQQQ1BpgmgIbDwMwG6ApCkQDtTCzwBIvOIJBQtCEBTEa4iGY2RB/QGQAAogFkqggoQQJMUjegJiN
lPFYwDbBoh2SfKGhBQokSPICmw5OY+zQGAN5kYUNIICg2QKSdIHmbtq0yd7eHk9mcnZ2Auru6OgwMDDA
o6yzq4sdnnXYWAECiAWUmFhAWQPiIWAM4S8XgBELdCXQbfiVsbPD0xvIWwABBMl60LACsoiwBhQ4jEwE
lLFDkhkbtMgBCCAWVkj2g8U5sjWZGZlnz59lA2cNSEnCBkmlLKzAJANXNnvOnIcPHkCSLlAR0B8skGQM
TQwgEiCAWEDZDhxgkLIJOTTcPdz19PUgSQ8cf0wPHz68eeMG0DZkZYYG+kqKisxI4P37D2/evIaXbUAA
EEDgQhaSbsFlLbJvAgIC0IJi5cqV9+/dB7oQ2RoTE1M0ZefPn//06SOsnAHZBBBALEhFFSh08Ac60KVs
4ODArwyU9iGBC7WFFSCAYIU5rEhHDvRt27e/fvUKHhTAcHv29Ck7qEBkQ1Z2+fLlL1++QGskMPj85TPY
FhZoOcTCChBA4OwGLhaZQRkaJdBOHDt+/cY1FhZ4KQJyFrjYRQm0Bw8evHr5Cp7/oYUyLO+ygMs9gABi
gfuIDVx3IOsHlyJIhRMkh4ONQFEG1M8OKYoRxQMbcl3EwgoQQLCgY4GqQPZNbW0tZrgvWbLkyZMnyNZ4
eHpiKrt+/fq3b9+g7mdhAQgg9KqJYPYGl2HsBHMxC7wcB1cfAAEEjiWkGpagNZAQIkIZC7iRA03EAAHE
aGdnh2wNpHaFMYDuhjPZ4HHDCinXYPHFBmtkQKKchQXOgNa1QP8ABBCk8oPW30gMVrCZ7KxwG9hQWRDj
wXxo+EDCCBwTEDFgrmcF53pgQgYIIBaEqWwsyKYh6nGoKMx4RLOFHVypscJSD8IvLNAMwgKvvAACiIUd
6n+wbnZoTcSO1P6B5hoW5JCCF71IloCzPisspJhhVS+kLgYIIEipgGQoNKdg8Q1SrmNDTpwssKob6gdW
aIMR3pwApheAAGKBVD+wVg8bG7zJgFyrQ6INLAsvQaB2QAhmaNIFWwluCzHDG92gcgoggFigjmdDqoYQ
NrOxIbUiYI0AaMqCewIaI6D8AbaIGQHBDUpmYDMcIIDAQY6IYjZYXMDCDBYLrPCECC2V4AHGBm/+QNp0
sFYqMwuscQzMywABBC0KkaMBViqxonoF0vhDatxAynSIL1jhDS5QCIGtgTZdIbkVIIDASQCSJcH5AErB
Cj+UCEeyAt46hCYrZmi6ZUbUB6AWE7xQAAgghG/gOQLRpEMth1ASFbTlxgJvN0LaLKDaHlyfM6KWRgAB
BgDTG34EXY2OPQAAAABJRU5ErkJggg==
"""),
('chrome/locale/en-US/%(lname)s.dtd',
"""
[menuitem]
[/menuitem]
[contextmenu]
[/contextmenu]
"""),
('chrome/locale/en-US/%(lname)s.properties',
"""
# $Id$
initError=Failed to initialize %%1.
extensions.%(lname)s@einaregilsson.com.description=%(descr)s
""")
)
generate()