From: robk-tahoe Date: Thu, 24 Jan 2008 04:06:41 +0000 (-0700) Subject: cleanup mac and windows build code X-Git-Tag: allmydata-tahoe-0.8.0~234 X-Git-Url: https://git.rkrishnan.org/%5B/%5D%20/uri/%22doc.html/running.html?a=commitdiff_plain;h=5085c35002f09b78abfe1269422958e597058e5f;p=tahoe-lafs%2Ftahoe-lafs.git cleanup mac and windows build code this moves some of the code common to both windows and mac builds into the allmydata module hierarchy, and cleans up the windows and mac build directories to import the code from there. --- diff --git a/mac/allmydata_tahoe.py b/mac/allmydata_tahoe.py index 3e29238a..b87d5cd8 100644 --- a/mac/allmydata_tahoe.py +++ b/mac/allmydata_tahoe.py @@ -1,137 +1,15 @@ -import pkgreshook # override the pkg_resources zip provider for py2app deployment -pkgreshook.install() # this is done before nevow is imported by depends +from allmydata.util import pkgresutil # override the pkg_resources zip provider for py2app deployment +pkgresutil.install() # this is done before nevow is imported by depends import depends # import dependencies so that py2exe finds them _junk = depends # appease pyflakes import sys -import os -import stat -import traceback - -TRY_TO_INSTALL_TAHOE_SCRIPT = True -TAHOE_SCRIPT = '''#!/bin/bash -if [ "x${@}x" == "xx" ] -then - %(exe)s --help -else - %(exe)s "${@}" -fi -''' - -def run_default_node(): - import operator - - basedir = os.path.expanduser('~/.tahoe') - if not os.path.isdir(basedir): - app_supp = os.path.expanduser('~/Library/Application Support/Allmydata Tahoe/') - if not os.path.isdir(app_supp): - os.makedirs(app_supp) - os.symlink(app_supp, basedir) - - if not os.path.exists(os.path.join(basedir, 'webport')): - f = file(os.path.join(basedir, 'webport'), 'wb') - f.write('8123') - f.close() - - def files_exist(file_list): - extant_conf = [ os.path.exists(os.path.join(basedir, f)) for f in file_list ] - return reduce(operator.__and__, extant_conf) - - def is_config_incomplete(): - necessary_conf_files = ['introducer.furl', 'private/root_dir.cap'] - need_config = not files_exist(necessary_conf_files) - if need_config: - print 'some config is missing from basedir (%s): %s' % (basedir, necessary_conf_files) - return need_config - - if is_config_incomplete(): - #import wx - from confwiz import ConfWizApp - app = ConfWizApp() - app.MainLoop() - - if is_config_incomplete(): - print 'config still incomplete; confwiz cancelled, exiting' - return 1 - - from twisted.internet import reactor - from twisted.python import log, logfile - from allmydata import client - # set up twisted logging. this will become part of the node rsn. - logdir = os.path.join(basedir, 'logs') - if not os.path.exists(logdir): - os.makedirs(logdir) - lf = logfile.LogFile('tahoesvc.log', logdir) - log.startLogging(lf) - - def webopen(): - if files_exist(['node.url', 'private/root_dir.cap']): - def read_file(f): - fh = file(f, 'rb') - contents = fh.read().strip() - fh.close() - return contents - import urllib, webbrowser - nodeurl = read_file(os.path.join(basedir, 'node.url')) - if nodeurl[-1] != "/": - nodeurl += "/" - root_dir = read_file(os.path.join(basedir, 'private/root_dir.cap')) - url = nodeurl + "uri/%s/" % urllib.quote(root_dir) - webbrowser.open(url) - else: - print 'files missing, not opening initial webish root page' - - def maybe_install_tahoe_script(): - path_candidates = ['/usr/local/bin', '~/bin', '~/Library/bin'] - env_path = map(os.path.expanduser, os.environ['PATH'].split(':')) - if not sys.executable.endswith('/python'): - print 'not installing tahoe script: unexpected sys.exe "%s"' % (sys.executable,) - return - for path_candidate in map(os.path.expanduser, env_path): - tahoe_path = path_candidate + '/tahoe' - if os.path.exists(tahoe_path): - print 'not installing "tahoe": it already exists at "%s"' % (tahoe_path,) - return - for path_candidate in map(os.path.expanduser, path_candidates): - if path_candidate not in env_path: - print path_candidate, 'not in', env_path - continue - tahoe_path = path_candidate + '/tahoe' - try: - print 'trying to install "%s"' % (tahoe_path,) - bin_path = (sys.executable[:-6] + 'Allmydata Tahoe').replace(' ', '\\ ') - script = TAHOE_SCRIPT % { 'exe': bin_path } - f = file(tahoe_path, 'wb') - f.write(script) - f.close() - mode = stat.S_IRUSR|stat.S_IXUSR|stat.S_IRGRP|stat.S_IXGRP|stat.S_IROTH|stat.S_IXOTH - os.chmod(tahoe_path, mode) - print 'installed "%s"' % (tahoe_path,) - return - except: - print 'unable to write %s' % (tahoe_path,) - traceback.print_exc() - else: - print 'no remaining candidate paths for installation of tahoe script' - - if TRY_TO_INSTALL_TAHOE_SCRIPT: - maybe_install_tahoe_script() - - # run the node itself - os.chdir(basedir) - c = client.Client(basedir) - reactor.callLater(0, c.startService) # after reactor startup - reactor.callLater(4, webopen) # give node a chance to connect before loading root dir - reactor.run() - - return 0 - - def main(argv): if len(argv) == 1: # then we were given no args; do default mac node startup - sys.exit(run_default_node()) + from allmydata.gui.macapp import run_macapp + sys.exit(run_macapp()) else: # given any cmd line args, do 'tahoe' cli behaviour from allmydata.scripts import runner diff --git a/mac/amdicon.py b/mac/amdicon.py deleted file mode 100644 index a26ca3c3..00000000 --- a/mac/amdicon.py +++ /dev/null @@ -1,69 +0,0 @@ -#---------------------------------------------------------------------- -# This file was generated by encode_icons.py -# -from wx import ImageFromStream, BitmapFromImage -from wx import EmptyIcon -import cStringIO - - -def getData(): - return \ -'\x89PNG\r\n\x1a\n\x00\x00\x00\rIHDR\x00\x00\x00 \x00\x00\x00 \x08\x06\x00\ -\x00\x00szz\xf4\x00\x00\x00\x04sBIT\x08\x08\x08\x08|\x08d\x88\x00\x00\x04\ -\x1aIDATX\x85\xad\x97MLTW\x14\xc7\xff\xef\xbd\x997|\x8c\x86\xb1\x888\x0c\x06\ -\x17\x80\x03\xa1\x8a\t\xa9\x8d5a\xd3t\xd3\xa4\xed\xae+\xe3\xa6\xe9\x02v\x8d\ -\xdd\xb8\xd2%D\xb1\x06\x02]\xd9.\xba\xd0\xa4iBqaHHM\xcbnbGZeH\x8d\x16\xad\ -\xed\x14\x91\xe1c\x98\xb9\xf7\xbdw\xcf\xe9\x02\x9c\xf2\xf1\xde\x9b7\xc8\x99L\ -2\x99{\xce\xb9\xbfs\xee\xb9\xe7\xde\xabi\xba\x81\xa0\x12\x1eN2\xd9!\x90\x1d\ -\xc2\xdb\x87\x92\xa8\xab\x8abY\xe41\xb34\x0b=\xec\xc00mX}\x19-\xb0C\x00\xd0t\ -#\xd0\xd7\xb8\xde\xcd-\xa3\x1f\xf3\xcd\x99\t\xce\x895\xde*9\xb1\xc67g&\xb8e\ -\xec#\x0e}u\x8a\x83\xfa\xd4t#\x18\x80q\xed4_\xb8s\x85\xcbIN\xac\xf1\x85;W\ -\xd8\xb8v:0D\xf9\xc9\x87\xba\xf9\xfc\xc4eV;>S\xf3)\x9e\x9aO\xf1\xfdlf\xd7\ -\xd8\xf9\x89\xcbl\\\xef\x0e\x06\xe1W\x03\xa1\x1b\x1d|&\xf6.\xee~:T\xfao\xe2\ -\x8fi\\\xfci\x04\x7f\x15\x9e\x03:\x03\xa4!Q\xd3\x8c\xc1\xde>|\xd8z\xb6\xa4w\ -\xe6\xdb\xcf\x90\x113\xb0\xfbg\xfdk\xa2\\\xea\xc7\x9fL\xf1\x92\xbd\xc8K\xf6"\ -\x8f\xa4o\xb16\xd8\xc3\x91\xd1\xcem\xd1EF;Y\x1b\xec\xe1\x91\xf4\xad\x92\xee\ -\xf8\x93\xa9@K\xa1\xfb\xc1\xc5\xab\xe2\xe8ij\x83$\x81\x97\xc5W\xb8to\x0cf\ -\xb4\xb0\xab\xd2\xad\xbe\x8cfF\x0b\xb8to\x0c/\x8b\xaf I\xa0\xa7\xa9\r\xf1\ -\xea\xb8\xff\x0e\x00\xbc\x01B7:\xf8\x9dD\x12\x92\x05$\x0b|\xf7p\x12y\xe4<\ -\xb7\x99\xd5\x97\xd1\xf2\xc8\xe1\xc7\xc7\xd3%\x9bd\xfd1\x84\x87\x93\xbc\'\ -\x00\x008z \x06I\x02\x92\x04rb\x15\x9a\xa1|\xa3\xd1\x0c\x85\xf9\x95l\xc9\xa6\ -\xbd>\x01&\xff\x12\x08\xf9\r:\xec@\x92(\xfd\x0e"\x95\xda\x94\x01\xb0\xb78\ -\xb3\x03\x02Tf\xe3\t\xa0\xa4\t\x87\x1d\x08*\x02\x00\xea\xa3Qt\x1e\xec\x00\ -\xbe\xe9\xf0]\xd3\xfah\xb4d\xe3\xb0\x03%M_\x00\xd7>\xa0\r\x9e\xe2/\xce~\x82\ -\x0f\xdaO\x96\x8d\xa0\x9c\xdc\x9d{\x80\xab\xd3?\x80/\xa6]\x8b\xc15\x03-\x07\ -\xe3\xe8mm/\xa5\xf2M\xa4\xb7\xb5\x1d\xdf\xff\x16\xc7S\xa4]\xc7]\x01\xaa\xcd\ -\xf0\xbeL\xbe\xd5\x9f\x97\xb8\x020\x13\xc4>\x020Se\x00\x04\x82do\x80\xb9\xec\ -\x02&\x1feP\xb0,\xd4\x98&\xde\xef8\x81\xf6\xc6\x06O}B\xa5\x00L\xa5J\xde)\x0f\ -\x9e\xfd\x83\xaf\x7f\xfe\x05\xe1\xda"\xec\xfeY-<\x9c\xe4\xfb\x93\x7f\xe2\xf3\ -s\xef\xe1\xe4\xb1\xa3\xee\x00{\xca\x80\xcb\x12,;K\xb8\x9dJo;\x0f\xec\xfeY\ -\xcd\x1c9\xc1\xb7S\xbf\xe2\xad\x06\x0bu\xa1\x18\xc2\xba\xb9\xcb\xdf\x1e\x00$\ -\x14;X\xb0\xb3\xf8\xd7z\x81U\xb5\x02b\x85e\xa1\x83\xbf\xdc}\x18\xd9\x03\xd5<\ -\x99\x1b\x07\x81P\xa5W\xe3p\xf8\x08\x8eW\xb5\xe1\x88\x19\xaf\x1c\x80\x99\xf0\ -B>\xc3\xbc|\x0c\x8b,\x10\x14\x14\x13\x88\x15\x98j\\\x1d1i\x90,A\xacP\xa0u,\ -\xda\x0bx\xb8\x9e\xc6a\xb3\x11k\x8ew}\xb8\x1eFy\xb5\x86\xb9\xe2\xef(\xa8\xf5\ -\xcd\x83E\xc2\xa2\x8d\x13\xae\xb1Y\xc0\x18\xea\xda\xd6\r\x8d\xa1.\x8e5\xadl\ -\xeaHX$7\xecX\xe2\xb9x\x8aU\xb5R\x19\xc0\xeb~.Y\xc2\xe2\xff\x9dY$\xd1p|\t\ -\xb5Q\xa7\x04a\x0cuq\xa4V\xa2\xae\xe5\xefM\x1d\x01\x8b$\x1c\xb672\x06\xdf\ -\xce\xed]\x03\x16I((\x10+\x106\xd2\xafX\x81\x0cB]3!\xff\xa8\x11\x00\xc0\xac\ -\xe1@"\x0bG/\x80\xc9\x7f\xb2\xe0\x00\xbc\xd1\x07\x88is\xfd\xb7C\xd8\xac\xef\ -\xd2/\x17iE\x00\xbc3\x03L\xdb\xb2\xe1\x90wk\xdd\x17\x00\x02C\x92\x00\x816\ -\xa3W`\xe6=GY9\x00\x13,\x96\xbe\xa9%+\x04m\xa0\x9b\xc9\xaa\xec%\x16\x08\x80\ -\xc1P\xec}\xff\x8b\xd4\xad"q.\xf5F\x13\xbf\x16\xd7mHN\xf0\x07k\x10\xf1\xf3\ -\xe7\n\xa0\xa4\x89\xe2bl_&/.\xc6\xa0D\xc4s\xdc\xf3i\xa6\rt\xb3Q%\xa1\x87\xfc\ -\xaf\xe2~B\x8e\x01%M\xcf\xeb\x18\x00\xfc\x07\x9aY\xdf_&\xed\xfd\xe8\x00\x00\ -\x00\x00IEND\xaeB`\x82' - -def getBitmap(): - return BitmapFromImage(getImage()) - -def getImage(): - stream = cStringIO.StringIO(getData()) - return ImageFromStream(stream) - -def getIcon(): - icon = EmptyIcon() - icon.CopyFromBitmap(getBitmap()) - return icon - - diff --git a/mac/confwiz.py b/mac/confwiz.py deleted file mode 100644 index 6860df5f..00000000 --- a/mac/confwiz.py +++ /dev/null @@ -1,407 +0,0 @@ - -BACKEND_URL = 'https://www-test.allmydata.com/native_client.php' -#REGISTER_PAGE = 'https://www-test.allmydata.com/register' -TAHOESVC_NAME = 'Tahoe' -WINFUSESVC_NAME = 'Allmydata Tahoe SMB' - -import os -import sys -#import time -import traceback -import urllib2 -from urllib import urlencode -#import webbrowser -import wx - -from allmydata.util.assertutil import precondition -from allmydata import uri - -import amdicon - - -class AuthError(Exception): - pass - -def unicode_to_utf8(uobj): - assert precondition(isinstance(uobj, unicode)) - return uobj.encode('utf-8') - - -def post(url, args): - argstr = urlencode(args) - conn = urllib2.urlopen(url, argstr) - return conn.read() - -def get_root_cap(url, user, passwd): - args = { - 'action': 'authenticate', - 'email': unicode_to_utf8(user), - 'passwd': unicode_to_utf8(passwd), - } - root_cap = post(url, args) - if root_cap == '0': - raise AuthError() - elif not uri.is_uri(root_cap): - raise ValueError('%r is not a URI' % (root_cap,)) - else: - return root_cap - -def create_account(url, user, passwd, subscribe): - args = { - 'action': 'create_account', - 'email': unicode_to_utf8(user), - 'passwd': unicode_to_utf8(passwd), - 'subscribe': subscribe and 'true' or 'false', - } - result_code = post(url, args) - return result_code - -def get_introducer_furl(url): - return post(url, { 'action': 'getintroducerfurl' }) - -def write_config_file(filename, contents): - if sys.platform == 'win32': - from allmydata.windows import registry - basedir = registry.get_base_dir_path() - else: - basedir = os.path.expanduser('~/.tahoe') - path = os.path.join(basedir, filename) - dirname = os.path.dirname(path) - if not os.path.exists(dirname): - os.makedirs(dirname) - iff = file(path, 'wb') - iff.write(contents) - iff.close() - - -def DisplayTraceback(message): - xc = traceback.format_exception(*sys.exc_info()) - wx.MessageBox(u"%s\n (%s)"%(message,''.join(xc)), 'Error') - -class ConfWizApp(wx.App): - def __init__(self): - wx.App.__init__(self, 0) - - def OnInit(self): - try: - wx.InitAllImageHandlers() - - self.login_frame = LoginFrame(self) - self.login_frame.CenterOnScreen() - self.SetTopWindow(self.login_frame) - #self.SetExitOnFrameDelete(True) - self.login_frame.Show(True) - - return True - except: - DisplayTraceback('config wizard init threw an exception') - - def swap_to_register_frame(self): - try: - self.login_frame.Show(False) - self.regiser_frame = RegisterFrame(self) - self.regiser_frame.CenterOnScreen() - self.SetTopWindow(self.regiser_frame) - self.SetExitOnFrameDelete(True) - self.regiser_frame.Show(True) - except: - DisplayTraceback('config wizard threw an exception') - -class LoginFrame(wx.Frame): - def __init__(self, app): - title = 'Allmydata Tahoe Config Wizard' - wx.Frame.__init__(self, None, -1, title) - self.app = app - self.SetSizeHints(100, 100, 600, 800) - self.SetIcon(amdicon.getIcon()) - self.Bind(wx.EVT_CLOSE, self.close) - - background = wx.Panel(self, -1) - background.parent = self - self.login_panel = LoginPanel(background) - self.reg_btn_panel = RegisterButtonPanel(background, app) - sizer = wx.BoxSizer(wx.VERTICAL) - background_sizer = wx.BoxSizer(wx.VERTICAL) - background_sizer.Add(self.login_panel, 1, wx.ALIGN_CENTER_HORIZONTAL | wx.ALL, 26) - background_sizer.Add(self.reg_btn_panel, 0, wx.ALIGN_CENTER_HORIZONTAL | wx.ALL, 26) - background.SetSizer(background_sizer) - sizer.Add(background, 0, wx.EXPAND | wx.ALL, 0) - self.SetSizer(sizer) - self.SetAutoLayout(True) - self.Fit() - self.Layout() - - def close(self, event): - self.Show(False) - self.app.ExitMainLoop() - -class RegisterFrame(wx.Frame): - def __init__(self, app): - title = 'Allmydata Tahoe Config Wizard' - wx.Frame.__init__(self, None, -1, title) - self.app = app - self.SetSizeHints(100, 100, 600, 800) - self.SetIcon(amdicon.getIcon()) - self.Bind(wx.EVT_CLOSE, self.close) - - background = wx.Panel(self, -1) - background.parent = self - self.register_panel = RegisterPanel(background) - sizer = wx.BoxSizer(wx.VERTICAL) - background_sizer = wx.BoxSizer(wx.VERTICAL) - background_sizer.Add(self.register_panel, 0, wx.ALIGN_CENTER_HORIZONTAL | wx.ALL, 26) - background.SetSizer(background_sizer) - sizer.Add(background, 0, wx.EXPAND | wx.ALL, 0) - self.SetSizer(sizer) - self.SetAutoLayout(True) - self.Fit() - self.Layout() - - def close(self, event): - self.Show(False) - self.app.ExitMainLoop() - - -class LoginPanel(wx.Panel): - def __init__(self, parent): - wx.Panel.__init__(self, parent, -1) - self.parent = parent - - self.sizer = wx.BoxSizer(wx.VERTICAL) - - self.user_label = wx.StaticText(self, -1, 'Email') - self.pass_label = wx.StaticText(self, -1, 'Password') - self.user_field = wx.TextCtrl(self, -1, u'', size=(260,-1)) - self.pass_field = wx.TextCtrl(self, -1, u'', size=(260,-1), style=wx.TE_PASSWORD) - self.login_button = wx.Button(self, -1, 'Sign In') - self.warning_label = wx.StaticText(self, -1, '') - self.warning_label.SetOwnForegroundColour(wx.RED) - wx.EVT_CHAR(self.user_field, self.on_user_entry) - wx.EVT_CHAR(self.pass_field, self.on_pass_entry) - self.Bind(wx.EVT_BUTTON, self.on_login, self.login_button) - login_sizer = wx.FlexGridSizer(3, 2, 5, 4) - login_sizer.Add(self.user_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.user_field, 0, wx.EXPAND | wx.ALL, 2) - login_sizer.Add(self.pass_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.pass_field, 0, wx.EXPAND | wx.ALL, 2) - login_sizer.Add(wx.Size(2,2), 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.login_button, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - self.sizer.Add(login_sizer, 1, wx.EXPAND | wx.ALL, 2) - self.sizer.Add(self.warning_label, 0, wx.CENTER | wx.ALL, 2) - self.SetSizer(self.sizer) - self.SetAutoLayout(True) - - def on_user_entry(self, event): - if event.GetKeyCode() == wx.WXK_RETURN: - self.pass_field.SetFocus() - else: - event.Skip() - - def on_pass_entry(self, event): - if event.GetKeyCode() == wx.WXK_RETURN: - self.on_login(event) - else: - event.Skip() - - def on_login(self, event): - user = self.user_field.GetValue() - passwd = self.pass_field.GetValue() - self.warning_label.SetLabel('Connecting...') - self.Layout() - wx.Yield() - - if passwd == '': - self.warning_label.SetLabel('You must enter a password') - self.pass_field.SetFocus() - self.Layout() - return - - try: - root_cap = get_root_cap(BACKEND_URL, user, passwd) - write_config_file('private/root_dir.cap', root_cap+'\n') - except AuthError: - self.warning_label.SetLabel('Your email and/or password is incorrect') - self.user_field.SetFocus() - self.Layout() - return - - # fetch the introducer furl - ifurl = get_introducer_furl(BACKEND_URL) - write_config_file('introducer.furl', ifurl+'\n') - - # start service etc. - if sys.platform == 'win32': - self.start_windows_service(TAHOESVC_NAME) - self.start_windows_service(WINFUSESVC_NAME) - - # exit - self.parent.parent.Close() - - def start_windows_service(self, svc_name): - try: - import win32service - import win32serviceutil as wsu - if wsu.QueryServiceStatus(svc_name)[1] != win32service.SERVICE_RUNNING: - wsu.StartService(svc_name) - except: - DisplayTraceback('Failed to start windows service "%s"' % (svc_name,)) - -class RegisterButtonPanel(wx.Panel): - def __init__(self, parent, app): - wx.Panel.__init__(self, parent, -1) - self.parent = parent - self.app = app - - self.sizer = wx.BoxSizer(wx.VERTICAL) - - self.reg_label = wx.StaticText(self, -1, "Don't have an account?") - self.reg_button = wx.Button(self, -1, 'Create Account') - self.Bind(wx.EVT_BUTTON, self.on_reg_button, self.reg_button) - reg_sizer = wx.FlexGridSizer(1, 2, 5, 4) - reg_sizer.Add(self.reg_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - reg_sizer.Add(self.reg_button, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - self.sizer.Add(reg_sizer, 1, wx.EXPAND | wx.ALL, 2) - self.SetSizer(self.sizer) - self.SetAutoLayout(True) - - def on_reg_button(self, event): - #webbrowser.open(REGISTER_PAGE) - self.app.swap_to_register_frame() - -class RegisterPanel(wx.Panel): - def __init__(self, parent): - wx.Panel.__init__(self, parent, -1) - self.parent = parent - - self.sizer = wx.BoxSizer(wx.VERTICAL) - - self.user_label = wx.StaticText(self, -1, 'Email') - self.pass_label = wx.StaticText(self, -1, 'Password') - self.conf_label = wx.StaticText(self, -1, 'Confirm Password') - self.user_field = wx.TextCtrl(self, -1, u'', size=(260,-1)) - self.pass_field = wx.TextCtrl(self, -1, u'', size=(260,-1), style=wx.TE_PASSWORD) - self.conf_field = wx.TextCtrl(self, -1, u'', size=(260,-1), style=wx.TE_PASSWORD) - self.create_account_button = wx.Button(self, -1, 'Create Account') - self.subscribe_box = wx.CheckBox(self, -1, 'Sign up for our Newsletter') - self.subscribe_box.SetValue(True) - self.warning_label = wx.StaticText(self, -1, '') - self.warning_label.SetOwnForegroundColour(wx.RED) - wx.EVT_CHAR(self.user_field, self.on_user_entry) - wx.EVT_CHAR(self.pass_field, self.on_pass_entry) - wx.EVT_CHAR(self.conf_field, self.on_conf_entry) - self.Bind(wx.EVT_BUTTON, self.on_create_account, self.create_account_button) - login_sizer = wx.FlexGridSizer(4, 2, 5, 4) - login_sizer.Add(self.user_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.user_field, 0, wx.EXPAND | wx.ALL, 2) - login_sizer.Add(self.pass_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.pass_field, 0, wx.EXPAND | wx.ALL, 2) - login_sizer.Add(self.conf_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.conf_field, 0, wx.EXPAND | wx.ALL, 2) - login_sizer.Add(wx.Size(2,2), 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.create_account_button, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - self.sizer.Add(login_sizer, 1, wx.EXPAND | wx.ALL, 2) - self.sizer.Add(self.warning_label, 0, wx.CENTER | wx.ALL, 2) - self.sizer.Add(self.subscribe_box, 0, wx.CENTER | wx.ALL, 2) - self.SetSizer(self.sizer) - self.SetAutoLayout(True) - - def on_user_entry(self, event): - if event.GetKeyCode() == wx.WXK_RETURN: - self.pass_field.SetFocus() - else: - event.Skip() - - def on_pass_entry(self, event): - if event.GetKeyCode() == wx.WXK_RETURN: - self.conf_field.SetFocus() - else: - event.Skip() - - def on_conf_entry(self, event): - if event.GetKeyCode() == wx.WXK_RETURN: - self.on_create_account(event) - else: - event.Skip() - - def on_create_account(self, event): - user = self.user_field.GetValue() - passwd = self.pass_field.GetValue() - pconf = self.conf_field.GetValue() - subscribe = self.subscribe_box.IsChecked() - self.warning_label.SetLabel('Connecting...') - self.Layout() - wx.Yield() - - if passwd == '': - self.warning_label.SetLabel('You must enter a password') - self.pass_field.SetFocus() - self.Layout() - return - - if passwd != pconf: - self.warning_label.SetLabel("Passwords don't match") - self.pass_field.SetValue('') - self.conf_field.SetValue('') - self.pass_field.SetFocus() - self.Layout() - return - - #print 'calling create_account', time.asctime() - result_code = create_account(BACKEND_URL, user, passwd, subscribe) - - if result_code == 'account_exists': - # try and log into it; if valid, use it anyway - try: - #print 'calling get_root_cap (ae)', time.asctime() - root_cap = get_root_cap(BACKEND_URL, user, passwd) - write_config_file('private/root_dir.cap', root_cap+'\n') - except AuthError: - self.warning_label.SetLabel('That email address is already registered') - self.user_field.SetFocus() - self.Layout() - return - elif result_code == 'error': - self.warning_label.SetLabel('an error occurred') - self.user_field.SetFocus() - self.Layout() - return - elif result_code == 'ok': - #print 'calling get_root_cap (ok)', time.asctime() - root_cap = get_root_cap(BACKEND_URL, user, passwd) - write_config_file('private/root_dir.cap', root_cap+'\n') - else: - self.warning_label.SetLabel('an unexpected error occurred ("%s")' % (result_code,)) - self.user_field.SetFocus() - self.Layout() - return - - # fetch the introducer furl - #print 'calling get_introducer_furl', time.asctime() - ifurl = get_introducer_furl(BACKEND_URL) - write_config_file('introducer.furl', ifurl+'\n') - - # start service etc. - if sys.platform == 'win32': - self.start_windows_service(TAHOESVC_NAME) - self.start_windows_service(WINFUSESVC_NAME) - - # exit - self.parent.parent.Close() - - def start_windows_service(self, svc_name): - try: - import win32service - import win32serviceutil as wsu - if wsu.QueryServiceStatus(svc_name)[1] != win32service.SERVICE_RUNNING: - wsu.StartService(svc_name) - except: - DisplayTraceback('Failed to start windows service "%s"' % (svc_name,)) - - -def main(): - app = ConfWizApp() - app.MainLoop() - - -if __name__ == '__main__': - main() diff --git a/mac/pkgreshook.py b/mac/pkgreshook.py deleted file mode 100644 index bb1d985c..00000000 --- a/mac/pkgreshook.py +++ /dev/null @@ -1,46 +0,0 @@ - -def install(): - """ - This installs a hook into setuptools' pkg_resources infrastructure, so that resource - files can be found in files relative to the runnin executable, in addition to the - usual egg and source lookup mechanisms. This overrides the ZipProvider, since that - is the lookup mechanism triggered within pkg_resources when running code out of a - py2exe or py2app build's library.zip. - """ - import os, sys - import pkg_resources, zipimport - - platform_libdirs = { - 'darwin': '../Resources/pkg_resources', - } - exedir = os.path.dirname(sys.executable) - libdir = platform_libdirs.get(sys.platform, 'pkg_resources') - - class Provider(pkg_resources.ZipProvider): - - def __init__(self, module): - self._module_name = module.__name__ - pkg_resources.ZipProvider.__init__(self, module) - - def get_resource_filename(self, manager, resource_name): - #print 'get_resource_filename(%s, %s)' % (manager, resource_name) - path = [exedir, libdir] + self._module_name.split('.') + [resource_name] - localfile = os.path.join(*path) - #print ' checking(%s)' % (localfile,) - if os.path.exists(localfile): - #print 'found locally' - return localfile - else: - try: - ret = pkg_resources.ZipProvider.get_resource_filename(self, manager, resource_name) - #print 'returning %s' % (ret,) - return ret - except NotImplementedError: - #print 'get_resource_filename(%s,%s): not found' % (self._module_name, resource_name) - #import traceback - #traceback.print_exc() - return '' - - pkg_resources.register_loader_type(zipimport.zipimporter, Provider) - - diff --git a/src/allmydata/gui/__init__.py b/src/allmydata/gui/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/allmydata/gui/amdicon.py b/src/allmydata/gui/amdicon.py new file mode 100644 index 00000000..a26ca3c3 --- /dev/null +++ b/src/allmydata/gui/amdicon.py @@ -0,0 +1,69 @@ +#---------------------------------------------------------------------- +# This file was generated by encode_icons.py +# +from wx import ImageFromStream, BitmapFromImage +from wx import EmptyIcon +import cStringIO + + +def getData(): + return \ +'\x89PNG\r\n\x1a\n\x00\x00\x00\rIHDR\x00\x00\x00 \x00\x00\x00 \x08\x06\x00\ +\x00\x00szz\xf4\x00\x00\x00\x04sBIT\x08\x08\x08\x08|\x08d\x88\x00\x00\x04\ +\x1aIDATX\x85\xad\x97MLTW\x14\xc7\xff\xef\xbd\x997|\x8c\x86\xb1\x888\x0c\x06\ +\x17\x80\x03\xa1\x8a\t\xa9\x8d5a\xd3t\xd3\xa4\xed\xae+\xe3\xa6\xe9\x02v\x8d\ +\xdd\xb8\xd2%D\xb1\x06\x02]\xd9.\xba\xd0\xa4iBqaHHM\xcbnbGZeH\x8d\x16\xad\ +\xed\x14\x91\xe1c\x98\xb9\xf7\xbdw\xcf\xe9\x02\x9c\xf2\xf1\xde\x9b7\xc8\x99L\ +2\x99{\xce\xb9\xbfs\xee\xb9\xe7\xde\xabi\xba\x81\xa0\x12\x1eN2\xd9!\x90\x1d\ +\xc2\xdb\x87\x92\xa8\xab\x8abY\xe41\xb34\x0b=\xec\xc00mX}\x19-\xb0C\x00\xd0t\ +#\xd0\xd7\xb8\xde\xcd-\xa3\x1f\xf3\xcd\x99\t\xce\x895\xde*9\xb1\xc67g&\xb8e\ +\xec#\x0e}u\x8a\x83\xfa\xd4t#\x18\x80q\xed4_\xb8s\x85\xcbIN\xac\xf1\x85;W\ +\xd8\xb8v:0D\xf9\xc9\x87\xba\xf9\xfc\xc4eV;>S\xf3)\x9e\x9aO\xf1\xfdlf\xd7\ +\xd8\xf9\x89\xcbl\\\xef\x0e\x06\xe1W\x03\xa1\x1b\x1d|&\xf6.\xee~:T\xfao\xe2\ +\x8fi\\\xfci\x04\x7f\x15\x9e\x03:\x03\xa4!Q\xd3\x8c\xc1\xde>|\xd8z\xb6\xa4w\ +\xe6\xdb\xcf\x90\x113\xb0\xfbg\xfdk\xa2\\\xea\xc7\x9fL\xf1\x92\xbd\xc8K\xf6"\ +\x8f\xa4o\xb16\xd8\xc3\x91\xd1\xcem\xd1EF;Y\x1b\xec\xe1\x91\xf4\xad\x92\xee\ +\xf8\x93\xa9@K\xa1\xfb\xc1\xc5\xab\xe2\xe8ij\x83$\x81\x97\xc5W\xb8to\x0cf\ +\xb4\xb0\xab\xd2\xad\xbe\x8cfF\x0b\xb8to\x0c/\x8b\xaf I\xa0\xa7\xa9\r\xf1\ +\xea\xb8\xff\x0e\x00\xbc\x01B7:\xf8\x9dD\x12\x92\x05$\x0b|\xf7p\x12y\xe4<\ +\xb7\x99\xd5\x97\xd1\xf2\xc8\xe1\xc7\xc7\xd3%\x9bd\xfd1\x84\x87\x93\xbc\'\ +\x00\x008z \x06I\x02\x92\x04rb\x15\x9a\xa1|\xa3\xd1\x0c\x85\xf9\x95l\xc9\xa6\ +\xbd>\x01&\xff\x12\x08\xf9\r:\xec@\x92(\xfd\x0e"\x95\xda\x94\x01\xb0\xb78\ +\xb3\x03\x02Tf\xe3\t\xa0\xa4\t\x87\x1d\x08*\x02\x00\xea\xa3Qt\x1e\xec\x00\ +\xbe\xe9\xf0]\xd3\xfah\xb4d\xe3\xb0\x03%M_\x00\xd7>\xa0\r\x9e\xe2/\xce~\x82\ +\x0f\xdaO\x96\x8d\xa0\x9c\xdc\x9d{\x80\xab\xd3?\x80/\xa6]\x8b\xc15\x03-\x07\ +\xe3\xe8mm/\xa5\xf2M\xa4\xb7\xb5\x1d\xdf\xff\x16\xc7S\xa4]\xc7]\x01\xaa\xcd\ +\xf0\xbeL\xbe\xd5\x9f\x97\xb8\x020\x13\xc4>\x020Se\x00\x04\x82do\x80\xb9\xec\ +\x02&\x1feP\xb0,\xd4\x98&\xde\xef8\x81\xf6\xc6\x06O}B\xa5\x00L\xa5J\xde)\x0f\ +\x9e\xfd\x83\xaf\x7f\xfe\x05\xe1\xda"\xec\xfeY-<\x9c\xe4\xfb\x93\x7f\xe2\xf3\ +s\xef\xe1\xe4\xb1\xa3\xee\x00{\xca\x80\xcb\x12,;K\xb8\x9dJo;\x0f\xec\xfeY\ +\xcd\x1c9\xc1\xb7S\xbf\xe2\xad\x06\x0bu\xa1\x18\xc2\xba\xb9\xcb\xdf\x1e\x00$\ +\x14;X\xb0\xb3\xf8\xd7z\x81U\xb5\x02b\x85e\xa1\x83\xbf\xdc}\x18\xd9\x03\xd5<\ +\x99\x1b\x07\x81P\xa5W\xe3p\xf8\x08\x8eW\xb5\xe1\x88\x19\xaf\x1c\x80\x99\xf0\ +B>\xc3\xbc|\x0c\x8b,\x10\x14\x14\x13\x88\x15\x98j\\\x1d1i\x90,A\xacP\xa0u,\ +\xda\x0bx\xb8\x9e\xc6a\xb3\x11k\x8ew}\xb8\x1eFy\xb5\x86\xb9\xe2\xef(\xa8\xf5\ +\xcd\x83E\xc2\xa2\x8d\x13\xae\xb1Y\xc0\x18\xea\xda\xd6\r\x8d\xa1.\x8e5\xadl\ +\xeaHX$7\xecX\xe2\xb9x\x8aU\xb5R\x19\xc0\xeb~.Y\xc2\xe2\xff\x9dY$\xd1p|\t\ +\xb5Q\xa7\x04a\x0cuq\xa4V\xa2\xae\xe5\xefM\x1d\x01\x8b$\x1c\xb672\x06\xdf\ +\xce\xed]\x03\x16I((\x10+\x106\xd2\xafX\x81\x0cB]3!\xff\xa8\x11\x00\xc0\xac\ +\xe1@"\x0bG/\x80\xc9\x7f\xb2\xe0\x00\xbc\xd1\x07\x88is\xfd\xb7C\xd8\xac\xef\ +\xd2/\x17iE\x00\xbc3\x03L\xdb\xb2\xe1\x90wk\xdd\x17\x00\x02C\x92\x00\x816\ +\xa3W`\xe6=GY9\x00\x13,\x96\xbe\xa9%+\x04m\xa0\x9b\xc9\xaa\xec%\x16\x08\x80\ +\xc1P\xec}\xff\x8b\xd4\xad"q.\xf5F\x13\xbf\x16\xd7mHN\xf0\x07k\x10\xf1\xf3\ +\xe7\n\xa0\xa4\x89\xe2bl_&/.\xc6\xa0D\xc4s\xdc\xf3i\xa6\rt\xb3Q%\xa1\x87\xfc\ +\xaf\xe2~B\x8e\x01%M\xcf\xeb\x18\x00\xfc\x07\x9aY\xdf_&\xed\xfd\xe8\x00\x00\ +\x00\x00IEND\xaeB`\x82' + +def getBitmap(): + return BitmapFromImage(getImage()) + +def getImage(): + stream = cStringIO.StringIO(getData()) + return ImageFromStream(stream) + +def getIcon(): + icon = EmptyIcon() + icon.CopyFromBitmap(getBitmap()) + return icon + + diff --git a/src/allmydata/gui/confwiz.py b/src/allmydata/gui/confwiz.py new file mode 100644 index 00000000..6860df5f --- /dev/null +++ b/src/allmydata/gui/confwiz.py @@ -0,0 +1,407 @@ + +BACKEND_URL = 'https://www-test.allmydata.com/native_client.php' +#REGISTER_PAGE = 'https://www-test.allmydata.com/register' +TAHOESVC_NAME = 'Tahoe' +WINFUSESVC_NAME = 'Allmydata Tahoe SMB' + +import os +import sys +#import time +import traceback +import urllib2 +from urllib import urlencode +#import webbrowser +import wx + +from allmydata.util.assertutil import precondition +from allmydata import uri + +import amdicon + + +class AuthError(Exception): + pass + +def unicode_to_utf8(uobj): + assert precondition(isinstance(uobj, unicode)) + return uobj.encode('utf-8') + + +def post(url, args): + argstr = urlencode(args) + conn = urllib2.urlopen(url, argstr) + return conn.read() + +def get_root_cap(url, user, passwd): + args = { + 'action': 'authenticate', + 'email': unicode_to_utf8(user), + 'passwd': unicode_to_utf8(passwd), + } + root_cap = post(url, args) + if root_cap == '0': + raise AuthError() + elif not uri.is_uri(root_cap): + raise ValueError('%r is not a URI' % (root_cap,)) + else: + return root_cap + +def create_account(url, user, passwd, subscribe): + args = { + 'action': 'create_account', + 'email': unicode_to_utf8(user), + 'passwd': unicode_to_utf8(passwd), + 'subscribe': subscribe and 'true' or 'false', + } + result_code = post(url, args) + return result_code + +def get_introducer_furl(url): + return post(url, { 'action': 'getintroducerfurl' }) + +def write_config_file(filename, contents): + if sys.platform == 'win32': + from allmydata.windows import registry + basedir = registry.get_base_dir_path() + else: + basedir = os.path.expanduser('~/.tahoe') + path = os.path.join(basedir, filename) + dirname = os.path.dirname(path) + if not os.path.exists(dirname): + os.makedirs(dirname) + iff = file(path, 'wb') + iff.write(contents) + iff.close() + + +def DisplayTraceback(message): + xc = traceback.format_exception(*sys.exc_info()) + wx.MessageBox(u"%s\n (%s)"%(message,''.join(xc)), 'Error') + +class ConfWizApp(wx.App): + def __init__(self): + wx.App.__init__(self, 0) + + def OnInit(self): + try: + wx.InitAllImageHandlers() + + self.login_frame = LoginFrame(self) + self.login_frame.CenterOnScreen() + self.SetTopWindow(self.login_frame) + #self.SetExitOnFrameDelete(True) + self.login_frame.Show(True) + + return True + except: + DisplayTraceback('config wizard init threw an exception') + + def swap_to_register_frame(self): + try: + self.login_frame.Show(False) + self.regiser_frame = RegisterFrame(self) + self.regiser_frame.CenterOnScreen() + self.SetTopWindow(self.regiser_frame) + self.SetExitOnFrameDelete(True) + self.regiser_frame.Show(True) + except: + DisplayTraceback('config wizard threw an exception') + +class LoginFrame(wx.Frame): + def __init__(self, app): + title = 'Allmydata Tahoe Config Wizard' + wx.Frame.__init__(self, None, -1, title) + self.app = app + self.SetSizeHints(100, 100, 600, 800) + self.SetIcon(amdicon.getIcon()) + self.Bind(wx.EVT_CLOSE, self.close) + + background = wx.Panel(self, -1) + background.parent = self + self.login_panel = LoginPanel(background) + self.reg_btn_panel = RegisterButtonPanel(background, app) + sizer = wx.BoxSizer(wx.VERTICAL) + background_sizer = wx.BoxSizer(wx.VERTICAL) + background_sizer.Add(self.login_panel, 1, wx.ALIGN_CENTER_HORIZONTAL | wx.ALL, 26) + background_sizer.Add(self.reg_btn_panel, 0, wx.ALIGN_CENTER_HORIZONTAL | wx.ALL, 26) + background.SetSizer(background_sizer) + sizer.Add(background, 0, wx.EXPAND | wx.ALL, 0) + self.SetSizer(sizer) + self.SetAutoLayout(True) + self.Fit() + self.Layout() + + def close(self, event): + self.Show(False) + self.app.ExitMainLoop() + +class RegisterFrame(wx.Frame): + def __init__(self, app): + title = 'Allmydata Tahoe Config Wizard' + wx.Frame.__init__(self, None, -1, title) + self.app = app + self.SetSizeHints(100, 100, 600, 800) + self.SetIcon(amdicon.getIcon()) + self.Bind(wx.EVT_CLOSE, self.close) + + background = wx.Panel(self, -1) + background.parent = self + self.register_panel = RegisterPanel(background) + sizer = wx.BoxSizer(wx.VERTICAL) + background_sizer = wx.BoxSizer(wx.VERTICAL) + background_sizer.Add(self.register_panel, 0, wx.ALIGN_CENTER_HORIZONTAL | wx.ALL, 26) + background.SetSizer(background_sizer) + sizer.Add(background, 0, wx.EXPAND | wx.ALL, 0) + self.SetSizer(sizer) + self.SetAutoLayout(True) + self.Fit() + self.Layout() + + def close(self, event): + self.Show(False) + self.app.ExitMainLoop() + + +class LoginPanel(wx.Panel): + def __init__(self, parent): + wx.Panel.__init__(self, parent, -1) + self.parent = parent + + self.sizer = wx.BoxSizer(wx.VERTICAL) + + self.user_label = wx.StaticText(self, -1, 'Email') + self.pass_label = wx.StaticText(self, -1, 'Password') + self.user_field = wx.TextCtrl(self, -1, u'', size=(260,-1)) + self.pass_field = wx.TextCtrl(self, -1, u'', size=(260,-1), style=wx.TE_PASSWORD) + self.login_button = wx.Button(self, -1, 'Sign In') + self.warning_label = wx.StaticText(self, -1, '') + self.warning_label.SetOwnForegroundColour(wx.RED) + wx.EVT_CHAR(self.user_field, self.on_user_entry) + wx.EVT_CHAR(self.pass_field, self.on_pass_entry) + self.Bind(wx.EVT_BUTTON, self.on_login, self.login_button) + login_sizer = wx.FlexGridSizer(3, 2, 5, 4) + login_sizer.Add(self.user_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) + login_sizer.Add(self.user_field, 0, wx.EXPAND | wx.ALL, 2) + login_sizer.Add(self.pass_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) + login_sizer.Add(self.pass_field, 0, wx.EXPAND | wx.ALL, 2) + login_sizer.Add(wx.Size(2,2), 0, wx.ALIGN_RIGHT | wx.ALL, 2) + login_sizer.Add(self.login_button, 0, wx.ALIGN_RIGHT | wx.ALL, 2) + self.sizer.Add(login_sizer, 1, wx.EXPAND | wx.ALL, 2) + self.sizer.Add(self.warning_label, 0, wx.CENTER | wx.ALL, 2) + self.SetSizer(self.sizer) + self.SetAutoLayout(True) + + def on_user_entry(self, event): + if event.GetKeyCode() == wx.WXK_RETURN: + self.pass_field.SetFocus() + else: + event.Skip() + + def on_pass_entry(self, event): + if event.GetKeyCode() == wx.WXK_RETURN: + self.on_login(event) + else: + event.Skip() + + def on_login(self, event): + user = self.user_field.GetValue() + passwd = self.pass_field.GetValue() + self.warning_label.SetLabel('Connecting...') + self.Layout() + wx.Yield() + + if passwd == '': + self.warning_label.SetLabel('You must enter a password') + self.pass_field.SetFocus() + self.Layout() + return + + try: + root_cap = get_root_cap(BACKEND_URL, user, passwd) + write_config_file('private/root_dir.cap', root_cap+'\n') + except AuthError: + self.warning_label.SetLabel('Your email and/or password is incorrect') + self.user_field.SetFocus() + self.Layout() + return + + # fetch the introducer furl + ifurl = get_introducer_furl(BACKEND_URL) + write_config_file('introducer.furl', ifurl+'\n') + + # start service etc. + if sys.platform == 'win32': + self.start_windows_service(TAHOESVC_NAME) + self.start_windows_service(WINFUSESVC_NAME) + + # exit + self.parent.parent.Close() + + def start_windows_service(self, svc_name): + try: + import win32service + import win32serviceutil as wsu + if wsu.QueryServiceStatus(svc_name)[1] != win32service.SERVICE_RUNNING: + wsu.StartService(svc_name) + except: + DisplayTraceback('Failed to start windows service "%s"' % (svc_name,)) + +class RegisterButtonPanel(wx.Panel): + def __init__(self, parent, app): + wx.Panel.__init__(self, parent, -1) + self.parent = parent + self.app = app + + self.sizer = wx.BoxSizer(wx.VERTICAL) + + self.reg_label = wx.StaticText(self, -1, "Don't have an account?") + self.reg_button = wx.Button(self, -1, 'Create Account') + self.Bind(wx.EVT_BUTTON, self.on_reg_button, self.reg_button) + reg_sizer = wx.FlexGridSizer(1, 2, 5, 4) + reg_sizer.Add(self.reg_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) + reg_sizer.Add(self.reg_button, 0, wx.ALIGN_RIGHT | wx.ALL, 2) + self.sizer.Add(reg_sizer, 1, wx.EXPAND | wx.ALL, 2) + self.SetSizer(self.sizer) + self.SetAutoLayout(True) + + def on_reg_button(self, event): + #webbrowser.open(REGISTER_PAGE) + self.app.swap_to_register_frame() + +class RegisterPanel(wx.Panel): + def __init__(self, parent): + wx.Panel.__init__(self, parent, -1) + self.parent = parent + + self.sizer = wx.BoxSizer(wx.VERTICAL) + + self.user_label = wx.StaticText(self, -1, 'Email') + self.pass_label = wx.StaticText(self, -1, 'Password') + self.conf_label = wx.StaticText(self, -1, 'Confirm Password') + self.user_field = wx.TextCtrl(self, -1, u'', size=(260,-1)) + self.pass_field = wx.TextCtrl(self, -1, u'', size=(260,-1), style=wx.TE_PASSWORD) + self.conf_field = wx.TextCtrl(self, -1, u'', size=(260,-1), style=wx.TE_PASSWORD) + self.create_account_button = wx.Button(self, -1, 'Create Account') + self.subscribe_box = wx.CheckBox(self, -1, 'Sign up for our Newsletter') + self.subscribe_box.SetValue(True) + self.warning_label = wx.StaticText(self, -1, '') + self.warning_label.SetOwnForegroundColour(wx.RED) + wx.EVT_CHAR(self.user_field, self.on_user_entry) + wx.EVT_CHAR(self.pass_field, self.on_pass_entry) + wx.EVT_CHAR(self.conf_field, self.on_conf_entry) + self.Bind(wx.EVT_BUTTON, self.on_create_account, self.create_account_button) + login_sizer = wx.FlexGridSizer(4, 2, 5, 4) + login_sizer.Add(self.user_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) + login_sizer.Add(self.user_field, 0, wx.EXPAND | wx.ALL, 2) + login_sizer.Add(self.pass_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) + login_sizer.Add(self.pass_field, 0, wx.EXPAND | wx.ALL, 2) + login_sizer.Add(self.conf_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) + login_sizer.Add(self.conf_field, 0, wx.EXPAND | wx.ALL, 2) + login_sizer.Add(wx.Size(2,2), 0, wx.ALIGN_RIGHT | wx.ALL, 2) + login_sizer.Add(self.create_account_button, 0, wx.ALIGN_RIGHT | wx.ALL, 2) + self.sizer.Add(login_sizer, 1, wx.EXPAND | wx.ALL, 2) + self.sizer.Add(self.warning_label, 0, wx.CENTER | wx.ALL, 2) + self.sizer.Add(self.subscribe_box, 0, wx.CENTER | wx.ALL, 2) + self.SetSizer(self.sizer) + self.SetAutoLayout(True) + + def on_user_entry(self, event): + if event.GetKeyCode() == wx.WXK_RETURN: + self.pass_field.SetFocus() + else: + event.Skip() + + def on_pass_entry(self, event): + if event.GetKeyCode() == wx.WXK_RETURN: + self.conf_field.SetFocus() + else: + event.Skip() + + def on_conf_entry(self, event): + if event.GetKeyCode() == wx.WXK_RETURN: + self.on_create_account(event) + else: + event.Skip() + + def on_create_account(self, event): + user = self.user_field.GetValue() + passwd = self.pass_field.GetValue() + pconf = self.conf_field.GetValue() + subscribe = self.subscribe_box.IsChecked() + self.warning_label.SetLabel('Connecting...') + self.Layout() + wx.Yield() + + if passwd == '': + self.warning_label.SetLabel('You must enter a password') + self.pass_field.SetFocus() + self.Layout() + return + + if passwd != pconf: + self.warning_label.SetLabel("Passwords don't match") + self.pass_field.SetValue('') + self.conf_field.SetValue('') + self.pass_field.SetFocus() + self.Layout() + return + + #print 'calling create_account', time.asctime() + result_code = create_account(BACKEND_URL, user, passwd, subscribe) + + if result_code == 'account_exists': + # try and log into it; if valid, use it anyway + try: + #print 'calling get_root_cap (ae)', time.asctime() + root_cap = get_root_cap(BACKEND_URL, user, passwd) + write_config_file('private/root_dir.cap', root_cap+'\n') + except AuthError: + self.warning_label.SetLabel('That email address is already registered') + self.user_field.SetFocus() + self.Layout() + return + elif result_code == 'error': + self.warning_label.SetLabel('an error occurred') + self.user_field.SetFocus() + self.Layout() + return + elif result_code == 'ok': + #print 'calling get_root_cap (ok)', time.asctime() + root_cap = get_root_cap(BACKEND_URL, user, passwd) + write_config_file('private/root_dir.cap', root_cap+'\n') + else: + self.warning_label.SetLabel('an unexpected error occurred ("%s")' % (result_code,)) + self.user_field.SetFocus() + self.Layout() + return + + # fetch the introducer furl + #print 'calling get_introducer_furl', time.asctime() + ifurl = get_introducer_furl(BACKEND_URL) + write_config_file('introducer.furl', ifurl+'\n') + + # start service etc. + if sys.platform == 'win32': + self.start_windows_service(TAHOESVC_NAME) + self.start_windows_service(WINFUSESVC_NAME) + + # exit + self.parent.parent.Close() + + def start_windows_service(self, svc_name): + try: + import win32service + import win32serviceutil as wsu + if wsu.QueryServiceStatus(svc_name)[1] != win32service.SERVICE_RUNNING: + wsu.StartService(svc_name) + except: + DisplayTraceback('Failed to start windows service "%s"' % (svc_name,)) + + +def main(): + app = ConfWizApp() + app.MainLoop() + + +if __name__ == '__main__': + main() diff --git a/src/allmydata/gui/macapp.py b/src/allmydata/gui/macapp.py new file mode 100644 index 00000000..d43cc823 --- /dev/null +++ b/src/allmydata/gui/macapp.py @@ -0,0 +1,138 @@ + +import sys +import os +import stat +import traceback + +TRY_TO_INSTALL_TAHOE_SCRIPT = True +TAHOE_SCRIPT = '''#!/bin/bash +if [ "x${@}x" == "xx" ] +then + %(exe)s --help +else + %(exe)s "${@}" +fi +''' + +def run_macapp(): + import operator + + basedir = os.path.expanduser('~/.tahoe') + if not os.path.isdir(basedir): + app_supp = os.path.expanduser('~/Library/Application Support/Allmydata Tahoe/') + if not os.path.isdir(app_supp): + os.makedirs(app_supp) + os.symlink(app_supp, basedir) + + if not os.path.exists(os.path.join(basedir, 'webport')): + f = file(os.path.join(basedir, 'webport'), 'wb') + f.write('8123') + f.close() + + def files_exist(file_list): + extant_conf = [ os.path.exists(os.path.join(basedir, f)) for f in file_list ] + return reduce(operator.__and__, extant_conf) + + def is_config_incomplete(): + necessary_conf_files = ['introducer.furl', 'private/root_dir.cap'] + need_config = not files_exist(necessary_conf_files) + if need_config: + print 'some config is missing from basedir (%s): %s' % (basedir, necessary_conf_files) + return need_config + + if is_config_incomplete(): + #import wx + from allmydata.gui.confwiz import ConfWizApp + app = ConfWizApp() + app.MainLoop() + + if is_config_incomplete(): + print 'config still incomplete; confwiz cancelled, exiting' + return 1 + + from twisted.internet import reactor + from twisted.python import log, logfile + from allmydata import client + # set up twisted logging. this will become part of the node rsn. + logdir = os.path.join(basedir, 'logs') + if not os.path.exists(logdir): + os.makedirs(logdir) + lf = logfile.LogFile('tahoesvc.log', logdir) + log.startLogging(lf) + + def webopen(): + if files_exist(['node.url', 'private/root_dir.cap']): + def read_file(f): + fh = file(f, 'rb') + contents = fh.read().strip() + fh.close() + return contents + import urllib, webbrowser + nodeurl = read_file(os.path.join(basedir, 'node.url')) + if nodeurl[-1] != "/": + nodeurl += "/" + root_dir = read_file(os.path.join(basedir, 'private/root_dir.cap')) + url = nodeurl + "uri/%s/" % urllib.quote(root_dir) + webbrowser.open(url) + else: + print 'files missing, not opening initial webish root page' + + def maybe_install_tahoe_script(): + path_candidates = ['/usr/local/bin', '~/bin', '~/Library/bin'] + env_path = map(os.path.expanduser, os.environ['PATH'].split(':')) + if not sys.executable.endswith('/python'): + print 'not installing tahoe script: unexpected sys.exe "%s"' % (sys.executable,) + return + for path_candidate in map(os.path.expanduser, env_path): + tahoe_path = path_candidate + '/tahoe' + if os.path.exists(tahoe_path): + print 'not installing "tahoe": it already exists at "%s"' % (tahoe_path,) + return + for path_candidate in map(os.path.expanduser, path_candidates): + if path_candidate not in env_path: + print path_candidate, 'not in', env_path + continue + tahoe_path = path_candidate + '/tahoe' + try: + print 'trying to install "%s"' % (tahoe_path,) + bin_path = (sys.executable[:-6] + 'Allmydata Tahoe').replace(' ', '\\ ') + script = TAHOE_SCRIPT % { 'exe': bin_path } + f = file(tahoe_path, 'wb') + f.write(script) + f.close() + mode = stat.S_IRUSR|stat.S_IXUSR|stat.S_IRGRP|stat.S_IXGRP|stat.S_IROTH|stat.S_IXOTH + os.chmod(tahoe_path, mode) + print 'installed "%s"' % (tahoe_path,) + return + except: + print 'unable to write %s' % (tahoe_path,) + traceback.print_exc() + else: + print 'no remaining candidate paths for installation of tahoe script' + + if TRY_TO_INSTALL_TAHOE_SCRIPT: + maybe_install_tahoe_script() + + # run the node itself + os.chdir(basedir) + c = client.Client(basedir) + reactor.callLater(0, c.startService) # after reactor startup + reactor.callLater(4, webopen) # give node a chance to connect before loading root dir + reactor.run() + + return 0 + + + +def main(argv): + if len(argv) == 1: + # then we were given no args; do default mac node startup + sys.exit(run_macapp()) + else: + # given any cmd line args, do 'tahoe' cli behaviour + from allmydata.scripts import runner + sys.exit(runner.runner(argv[1:], install_node_control=False)) + +if __name__ == '__main__': + main(sys.argv) + diff --git a/src/allmydata/util/pkgresutil.py b/src/allmydata/util/pkgresutil.py new file mode 100644 index 00000000..bb1d985c --- /dev/null +++ b/src/allmydata/util/pkgresutil.py @@ -0,0 +1,46 @@ + +def install(): + """ + This installs a hook into setuptools' pkg_resources infrastructure, so that resource + files can be found in files relative to the runnin executable, in addition to the + usual egg and source lookup mechanisms. This overrides the ZipProvider, since that + is the lookup mechanism triggered within pkg_resources when running code out of a + py2exe or py2app build's library.zip. + """ + import os, sys + import pkg_resources, zipimport + + platform_libdirs = { + 'darwin': '../Resources/pkg_resources', + } + exedir = os.path.dirname(sys.executable) + libdir = platform_libdirs.get(sys.platform, 'pkg_resources') + + class Provider(pkg_resources.ZipProvider): + + def __init__(self, module): + self._module_name = module.__name__ + pkg_resources.ZipProvider.__init__(self, module) + + def get_resource_filename(self, manager, resource_name): + #print 'get_resource_filename(%s, %s)' % (manager, resource_name) + path = [exedir, libdir] + self._module_name.split('.') + [resource_name] + localfile = os.path.join(*path) + #print ' checking(%s)' % (localfile,) + if os.path.exists(localfile): + #print 'found locally' + return localfile + else: + try: + ret = pkg_resources.ZipProvider.get_resource_filename(self, manager, resource_name) + #print 'returning %s' % (ret,) + return ret + except NotImplementedError: + #print 'get_resource_filename(%s,%s): not found' % (self._module_name, resource_name) + #import traceback + #traceback.print_exc() + return '' + + pkg_resources.register_loader_type(zipimport.zipimporter, Provider) + + diff --git a/windows/amdicon.py b/windows/amdicon.py deleted file mode 100644 index a26ca3c3..00000000 --- a/windows/amdicon.py +++ /dev/null @@ -1,69 +0,0 @@ -#---------------------------------------------------------------------- -# This file was generated by encode_icons.py -# -from wx import ImageFromStream, BitmapFromImage -from wx import EmptyIcon -import cStringIO - - -def getData(): - return \ -'\x89PNG\r\n\x1a\n\x00\x00\x00\rIHDR\x00\x00\x00 \x00\x00\x00 \x08\x06\x00\ -\x00\x00szz\xf4\x00\x00\x00\x04sBIT\x08\x08\x08\x08|\x08d\x88\x00\x00\x04\ -\x1aIDATX\x85\xad\x97MLTW\x14\xc7\xff\xef\xbd\x997|\x8c\x86\xb1\x888\x0c\x06\ -\x17\x80\x03\xa1\x8a\t\xa9\x8d5a\xd3t\xd3\xa4\xed\xae+\xe3\xa6\xe9\x02v\x8d\ -\xdd\xb8\xd2%D\xb1\x06\x02]\xd9.\xba\xd0\xa4iBqaHHM\xcbnbGZeH\x8d\x16\xad\ -\xed\x14\x91\xe1c\x98\xb9\xf7\xbdw\xcf\xe9\x02\x9c\xf2\xf1\xde\x9b7\xc8\x99L\ -2\x99{\xce\xb9\xbfs\xee\xb9\xe7\xde\xabi\xba\x81\xa0\x12\x1eN2\xd9!\x90\x1d\ -\xc2\xdb\x87\x92\xa8\xab\x8abY\xe41\xb34\x0b=\xec\xc00mX}\x19-\xb0C\x00\xd0t\ -#\xd0\xd7\xb8\xde\xcd-\xa3\x1f\xf3\xcd\x99\t\xce\x895\xde*9\xb1\xc67g&\xb8e\ -\xec#\x0e}u\x8a\x83\xfa\xd4t#\x18\x80q\xed4_\xb8s\x85\xcbIN\xac\xf1\x85;W\ -\xd8\xb8v:0D\xf9\xc9\x87\xba\xf9\xfc\xc4eV;>S\xf3)\x9e\x9aO\xf1\xfdlf\xd7\ -\xd8\xf9\x89\xcbl\\\xef\x0e\x06\xe1W\x03\xa1\x1b\x1d|&\xf6.\xee~:T\xfao\xe2\ -\x8fi\\\xfci\x04\x7f\x15\x9e\x03:\x03\xa4!Q\xd3\x8c\xc1\xde>|\xd8z\xb6\xa4w\ -\xe6\xdb\xcf\x90\x113\xb0\xfbg\xfdk\xa2\\\xea\xc7\x9fL\xf1\x92\xbd\xc8K\xf6"\ -\x8f\xa4o\xb16\xd8\xc3\x91\xd1\xcem\xd1EF;Y\x1b\xec\xe1\x91\xf4\xad\x92\xee\ -\xf8\x93\xa9@K\xa1\xfb\xc1\xc5\xab\xe2\xe8ij\x83$\x81\x97\xc5W\xb8to\x0cf\ -\xb4\xb0\xab\xd2\xad\xbe\x8cfF\x0b\xb8to\x0c/\x8b\xaf I\xa0\xa7\xa9\r\xf1\ -\xea\xb8\xff\x0e\x00\xbc\x01B7:\xf8\x9dD\x12\x92\x05$\x0b|\xf7p\x12y\xe4<\ -\xb7\x99\xd5\x97\xd1\xf2\xc8\xe1\xc7\xc7\xd3%\x9bd\xfd1\x84\x87\x93\xbc\'\ -\x00\x008z \x06I\x02\x92\x04rb\x15\x9a\xa1|\xa3\xd1\x0c\x85\xf9\x95l\xc9\xa6\ -\xbd>\x01&\xff\x12\x08\xf9\r:\xec@\x92(\xfd\x0e"\x95\xda\x94\x01\xb0\xb78\ -\xb3\x03\x02Tf\xe3\t\xa0\xa4\t\x87\x1d\x08*\x02\x00\xea\xa3Qt\x1e\xec\x00\ -\xbe\xe9\xf0]\xd3\xfah\xb4d\xe3\xb0\x03%M_\x00\xd7>\xa0\r\x9e\xe2/\xce~\x82\ -\x0f\xdaO\x96\x8d\xa0\x9c\xdc\x9d{\x80\xab\xd3?\x80/\xa6]\x8b\xc15\x03-\x07\ -\xe3\xe8mm/\xa5\xf2M\xa4\xb7\xb5\x1d\xdf\xff\x16\xc7S\xa4]\xc7]\x01\xaa\xcd\ -\xf0\xbeL\xbe\xd5\x9f\x97\xb8\x020\x13\xc4>\x020Se\x00\x04\x82do\x80\xb9\xec\ -\x02&\x1feP\xb0,\xd4\x98&\xde\xef8\x81\xf6\xc6\x06O}B\xa5\x00L\xa5J\xde)\x0f\ -\x9e\xfd\x83\xaf\x7f\xfe\x05\xe1\xda"\xec\xfeY-<\x9c\xe4\xfb\x93\x7f\xe2\xf3\ -s\xef\xe1\xe4\xb1\xa3\xee\x00{\xca\x80\xcb\x12,;K\xb8\x9dJo;\x0f\xec\xfeY\ -\xcd\x1c9\xc1\xb7S\xbf\xe2\xad\x06\x0bu\xa1\x18\xc2\xba\xb9\xcb\xdf\x1e\x00$\ -\x14;X\xb0\xb3\xf8\xd7z\x81U\xb5\x02b\x85e\xa1\x83\xbf\xdc}\x18\xd9\x03\xd5<\ -\x99\x1b\x07\x81P\xa5W\xe3p\xf8\x08\x8eW\xb5\xe1\x88\x19\xaf\x1c\x80\x99\xf0\ -B>\xc3\xbc|\x0c\x8b,\x10\x14\x14\x13\x88\x15\x98j\\\x1d1i\x90,A\xacP\xa0u,\ -\xda\x0bx\xb8\x9e\xc6a\xb3\x11k\x8ew}\xb8\x1eFy\xb5\x86\xb9\xe2\xef(\xa8\xf5\ -\xcd\x83E\xc2\xa2\x8d\x13\xae\xb1Y\xc0\x18\xea\xda\xd6\r\x8d\xa1.\x8e5\xadl\ -\xeaHX$7\xecX\xe2\xb9x\x8aU\xb5R\x19\xc0\xeb~.Y\xc2\xe2\xff\x9dY$\xd1p|\t\ -\xb5Q\xa7\x04a\x0cuq\xa4V\xa2\xae\xe5\xefM\x1d\x01\x8b$\x1c\xb672\x06\xdf\ -\xce\xed]\x03\x16I((\x10+\x106\xd2\xafX\x81\x0cB]3!\xff\xa8\x11\x00\xc0\xac\ -\xe1@"\x0bG/\x80\xc9\x7f\xb2\xe0\x00\xbc\xd1\x07\x88is\xfd\xb7C\xd8\xac\xef\ -\xd2/\x17iE\x00\xbc3\x03L\xdb\xb2\xe1\x90wk\xdd\x17\x00\x02C\x92\x00\x816\ -\xa3W`\xe6=GY9\x00\x13,\x96\xbe\xa9%+\x04m\xa0\x9b\xc9\xaa\xec%\x16\x08\x80\ -\xc1P\xec}\xff\x8b\xd4\xad"q.\xf5F\x13\xbf\x16\xd7mHN\xf0\x07k\x10\xf1\xf3\ -\xe7\n\xa0\xa4\x89\xe2bl_&/.\xc6\xa0D\xc4s\xdc\xf3i\xa6\rt\xb3Q%\xa1\x87\xfc\ -\xaf\xe2~B\x8e\x01%M\xcf\xeb\x18\x00\xfc\x07\x9aY\xdf_&\xed\xfd\xe8\x00\x00\ -\x00\x00IEND\xaeB`\x82' - -def getBitmap(): - return BitmapFromImage(getImage()) - -def getImage(): - stream = cStringIO.StringIO(getData()) - return ImageFromStream(stream) - -def getIcon(): - icon = EmptyIcon() - icon.CopyFromBitmap(getBitmap()) - return icon - - diff --git a/windows/confwiz.py b/windows/confwiz.py index 65c93e74..2a5e8cd6 100644 --- a/windows/confwiz.py +++ b/windows/confwiz.py @@ -1,405 +1,9 @@ -BACKEND_URL = 'https://www-test.allmydata.com/native_client.php' -#REGISTER_PAGE = 'https://www-test.allmydata.com/register' -TAHOESVC_NAME = 'Tahoe' -WINFUSESVC_NAME = 'Allmydata Tahoe SMB' - -import os -import sys -#import time -import traceback -import urllib2 -from urllib import urlencode -#import webbrowser -import wx - -from allmydata.util.assertutil import precondition -from allmydata import uri - -import amdicon - - -class AuthError(Exception): - pass - -def unicode_to_utf8(uobj): - assert precondition(isinstance(uobj, unicode)) - return uobj.encode('utf-8') - - -def post(url, args): - argstr = urlencode(args) - conn = urllib2.urlopen(url, argstr) - return conn.read() - -def get_root_cap(url, user, passwd): - args = { - 'action': 'authenticate', - 'email': unicode_to_utf8(user), - 'passwd': unicode_to_utf8(passwd), - } - root_cap = post(url, args) - if root_cap == '0': - raise AuthError() - elif not uri.is_uri(root_cap): - raise ValueError('%r is not a URI' % (root_cap,)) - else: - return root_cap - -def create_account(url, user, passwd, subscribe): - args = { - 'action': 'create_account', - 'email': unicode_to_utf8(user), - 'passwd': unicode_to_utf8(passwd), - 'subscribe': subscribe and 'true' or 'false', - } - result_code = post(url, args) - return result_code - -def get_introducer_furl(url): - return post(url, { 'action': 'getintroducerfurl' }) - -def write_config_file(filename, contents): - if sys.platform == 'win32': - from allmydata.windows import registry - basedir = registry.get_base_dir_path() - else: - basedir = os.path.expanduser('~/.tahoe') - path = os.path.join(basedir, filename) - dirname = os.path.dirname(path) - if not os.path.exists(dirname): - os.makedirs(dirname) - iff = file(path, 'wb') - iff.write(contents) - iff.close() - - -def DisplayTraceback(message): - xc = traceback.format_exception(*sys.exc_info()) - wx.MessageBox(u"%s\n (%s)"%(message,''.join(xc)), 'Error') - -class ConfWizApp(wx.App): - def __init__(self): - wx.App.__init__(self, 0) - - def OnInit(self): - try: - wx.InitAllImageHandlers() - - self.login_frame = LoginFrame(self) - self.login_frame.CenterOnScreen() - self.SetTopWindow(self.login_frame) - self.SetExitOnFrameDelete(True) - self.login_frame.Show(True) - - return True - except: - DisplayTraceback('config wizard init threw an exception') - - def swap_to_register_frame(self): - try: - self.login_frame.Show(False) - self.regiser_frame = RegisterFrame(self) - self.regiser_frame.CenterOnScreen() - self.SetTopWindow(self.regiser_frame) - self.SetExitOnFrameDelete(True) - self.regiser_frame.Show(True) - except: - DisplayTraceback('config wizard threw an exception') - -class LoginFrame(wx.Frame): - def __init__(self, app): - title = 'Allmydata Tahoe Config Wizard' - wx.Frame.__init__(self, None, -1, title) - self.app = app - self.SetSizeHints(100, 100, 600, 800) - self.SetIcon(amdicon.getIcon()) - self.Bind(wx.EVT_CLOSE, self.close) - - background = wx.Panel(self, -1) - background.parent = self - self.login_panel = LoginPanel(background) - self.reg_btn_panel = RegisterButtonPanel(background, app) - sizer = wx.BoxSizer(wx.VERTICAL) - background_sizer = wx.BoxSizer(wx.VERTICAL) - background_sizer.Add(self.login_panel, 1, wx.ALIGN_CENTER_HORIZONTAL | wx.ALL, 26) - background_sizer.Add(self.reg_btn_panel, 0, wx.ALIGN_CENTER_HORIZONTAL | wx.ALL, 26) - background.SetSizer(background_sizer) - sizer.Add(background, 0, wx.EXPAND | wx.ALL, 0) - self.SetSizer(sizer) - self.SetAutoLayout(True) - self.Fit() - self.Layout() - - def close(self, event): - sys.exit() - -class RegisterFrame(wx.Frame): - def __init__(self, app): - title = 'Allmydata Tahoe Config Wizard' - wx.Frame.__init__(self, None, -1, title) - self.app = app - self.SetSizeHints(100, 100, 600, 800) - self.SetIcon(amdicon.getIcon()) - self.Bind(wx.EVT_CLOSE, self.close) - - background = wx.Panel(self, -1) - background.parent = self - self.register_panel = RegisterPanel(background) - sizer = wx.BoxSizer(wx.VERTICAL) - background_sizer = wx.BoxSizer(wx.VERTICAL) - background_sizer.Add(self.register_panel, 0, wx.ALIGN_CENTER_HORIZONTAL | wx.ALL, 26) - background.SetSizer(background_sizer) - sizer.Add(background, 0, wx.EXPAND | wx.ALL, 0) - self.SetSizer(sizer) - self.SetAutoLayout(True) - self.Fit() - self.Layout() - - def close(self, event): - sys.exit() - - -class LoginPanel(wx.Panel): - def __init__(self, parent): - wx.Panel.__init__(self, parent, -1) - self.parent = parent - - self.sizer = wx.BoxSizer(wx.VERTICAL) - - self.user_label = wx.StaticText(self, -1, 'Email') - self.pass_label = wx.StaticText(self, -1, 'Password') - self.user_field = wx.TextCtrl(self, -1, u'', size=(260,-1)) - self.pass_field = wx.TextCtrl(self, -1, u'', size=(260,-1), style=wx.TE_PASSWORD) - self.login_button = wx.Button(self, -1, 'Sign In') - self.warning_label = wx.StaticText(self, -1, '') - self.warning_label.SetOwnForegroundColour(wx.RED) - wx.EVT_CHAR(self.user_field, self.on_user_entry) - wx.EVT_CHAR(self.pass_field, self.on_pass_entry) - self.Bind(wx.EVT_BUTTON, self.on_login, self.login_button) - login_sizer = wx.FlexGridSizer(3, 2, 5, 4) - login_sizer.Add(self.user_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.user_field, 0, wx.EXPAND | wx.ALL, 2) - login_sizer.Add(self.pass_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.pass_field, 0, wx.EXPAND | wx.ALL, 2) - login_sizer.Add(wx.Size(2,2), 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.login_button, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - self.sizer.Add(login_sizer, 1, wx.EXPAND | wx.ALL, 2) - self.sizer.Add(self.warning_label, 0, wx.CENTER | wx.ALL, 2) - self.SetSizer(self.sizer) - self.SetAutoLayout(True) - - def on_user_entry(self, event): - if event.GetKeyCode() == wx.WXK_RETURN: - self.pass_field.SetFocus() - else: - event.Skip() - - def on_pass_entry(self, event): - if event.GetKeyCode() == wx.WXK_RETURN: - self.on_login(event) - else: - event.Skip() - - def on_login(self, event): - user = self.user_field.GetValue() - passwd = self.pass_field.GetValue() - self.warning_label.SetLabel('Connecting...') - self.Layout() - wx.Yield() - - if passwd == '': - self.warning_label.SetLabel('You must enter a password') - self.pass_field.SetFocus() - self.Layout() - return - - try: - root_cap = get_root_cap(BACKEND_URL, user, passwd) - write_config_file('private/root_dir.cap', root_cap+'\n') - except AuthError: - self.warning_label.SetLabel('Your email and/or password is incorrect') - self.user_field.SetFocus() - self.Layout() - return - - # fetch the introducer furl - ifurl = get_introducer_furl(BACKEND_URL) - write_config_file('introducer.furl', ifurl+'\n') - - # start service etc. - if sys.platform == 'win32': - self.start_windows_service(TAHOESVC_NAME) - self.start_windows_service(WINFUSESVC_NAME) - - # exit - self.parent.parent.Close() - - def start_windows_service(self, svc_name): - try: - import win32service - import win32serviceutil as wsu - if wsu.QueryServiceStatus(svc_name)[1] != win32service.SERVICE_RUNNING: - wsu.StartService(svc_name) - except: - DisplayTraceback('Failed to start windows service "%s"' % (svc_name,)) - -class RegisterButtonPanel(wx.Panel): - def __init__(self, parent, app): - wx.Panel.__init__(self, parent, -1) - self.parent = parent - self.app = app - - self.sizer = wx.BoxSizer(wx.VERTICAL) - - self.reg_label = wx.StaticText(self, -1, "Don't have an account?") - self.reg_button = wx.Button(self, -1, 'Create Account') - self.Bind(wx.EVT_BUTTON, self.on_reg_button, self.reg_button) - reg_sizer = wx.FlexGridSizer(1, 2, 5, 4) - reg_sizer.Add(self.reg_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - reg_sizer.Add(self.reg_button, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - self.sizer.Add(reg_sizer, 1, wx.EXPAND | wx.ALL, 2) - self.SetSizer(self.sizer) - self.SetAutoLayout(True) - - def on_reg_button(self, event): - #webbrowser.open(REGISTER_PAGE) - self.app.swap_to_register_frame() - -class RegisterPanel(wx.Panel): - def __init__(self, parent): - wx.Panel.__init__(self, parent, -1) - self.parent = parent - - self.sizer = wx.BoxSizer(wx.VERTICAL) - - self.user_label = wx.StaticText(self, -1, 'Email') - self.pass_label = wx.StaticText(self, -1, 'Password') - self.conf_label = wx.StaticText(self, -1, 'Confirm Password') - self.user_field = wx.TextCtrl(self, -1, u'', size=(260,-1)) - self.pass_field = wx.TextCtrl(self, -1, u'', size=(260,-1), style=wx.TE_PASSWORD) - self.conf_field = wx.TextCtrl(self, -1, u'', size=(260,-1), style=wx.TE_PASSWORD) - self.create_account_button = wx.Button(self, -1, 'Create Account') - self.subscribe_box = wx.CheckBox(self, -1, 'Sign up for our Newsletter') - self.subscribe_box.SetValue(True) - self.warning_label = wx.StaticText(self, -1, '') - self.warning_label.SetOwnForegroundColour(wx.RED) - wx.EVT_CHAR(self.user_field, self.on_user_entry) - wx.EVT_CHAR(self.pass_field, self.on_pass_entry) - wx.EVT_CHAR(self.conf_field, self.on_conf_entry) - self.Bind(wx.EVT_BUTTON, self.on_create_account, self.create_account_button) - login_sizer = wx.FlexGridSizer(4, 2, 5, 4) - login_sizer.Add(self.user_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.user_field, 0, wx.EXPAND | wx.ALL, 2) - login_sizer.Add(self.pass_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.pass_field, 0, wx.EXPAND | wx.ALL, 2) - login_sizer.Add(self.conf_label, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.conf_field, 0, wx.EXPAND | wx.ALL, 2) - login_sizer.Add(wx.Size(2,2), 0, wx.ALIGN_RIGHT | wx.ALL, 2) - login_sizer.Add(self.create_account_button, 0, wx.ALIGN_RIGHT | wx.ALL, 2) - self.sizer.Add(login_sizer, 1, wx.EXPAND | wx.ALL, 2) - self.sizer.Add(self.warning_label, 0, wx.CENTER | wx.ALL, 2) - self.sizer.Add(self.subscribe_box, 0, wx.CENTER | wx.ALL, 2) - self.SetSizer(self.sizer) - self.SetAutoLayout(True) - - def on_user_entry(self, event): - if event.GetKeyCode() == wx.WXK_RETURN: - self.pass_field.SetFocus() - else: - event.Skip() - - def on_pass_entry(self, event): - if event.GetKeyCode() == wx.WXK_RETURN: - self.conf_field.SetFocus() - else: - event.Skip() - - def on_conf_entry(self, event): - if event.GetKeyCode() == wx.WXK_RETURN: - self.on_create_account(event) - else: - event.Skip() - - def on_create_account(self, event): - user = self.user_field.GetValue() - passwd = self.pass_field.GetValue() - pconf = self.conf_field.GetValue() - subscribe = self.subscribe_box.IsChecked() - self.warning_label.SetLabel('Connecting...') - self.Layout() - wx.Yield() - - if passwd == '': - self.warning_label.SetLabel('You must enter a password') - self.pass_field.SetFocus() - self.Layout() - return - - if passwd != pconf: - self.warning_label.SetLabel("Passwords don't match") - self.pass_field.SetValue('') - self.conf_field.SetValue('') - self.pass_field.SetFocus() - self.Layout() - return - - #print 'calling create_account', time.asctime() - result_code = create_account(BACKEND_URL, user, passwd, subscribe) - - if result_code == 'account_exists': - # try and log into it; if valid, use it anyway - try: - #print 'calling get_root_cap (ae)', time.asctime() - root_cap = get_root_cap(BACKEND_URL, user, passwd) - write_config_file('private/root_dir.cap', root_cap+'\n') - except AuthError: - self.warning_label.SetLabel('That email address is already registered') - self.user_field.SetFocus() - self.Layout() - return - elif result_code == 'error': - self.warning_label.SetLabel('an error occurred') - self.user_field.SetFocus() - self.Layout() - return - elif result_code == 'ok': - #print 'calling get_root_cap (ok)', time.asctime() - root_cap = get_root_cap(BACKEND_URL, user, passwd) - write_config_file('private/root_dir.cap', root_cap+'\n') - else: - self.warning_label.SetLabel('an unexpected error occurred ("%s")' % (result_code,)) - self.user_field.SetFocus() - self.Layout() - return - - # fetch the introducer furl - #print 'calling get_introducer_furl', time.asctime() - ifurl = get_introducer_furl(BACKEND_URL) - write_config_file('introducer.furl', ifurl+'\n') - - # start service etc. - if sys.platform == 'win32': - self.start_windows_service(TAHOESVC_NAME) - self.start_windows_service(WINFUSESVC_NAME) - - # exit - self.parent.parent.Close() - - def start_windows_service(self, svc_name): - try: - import win32service - import win32serviceutil as wsu - if wsu.QueryServiceStatus(svc_name)[1] != win32service.SERVICE_RUNNING: - wsu.StartService(svc_name) - except: - DisplayTraceback('Failed to start windows service "%s"' % (svc_name,)) - +from allmydata.gui.confwiz import ConfWizApp def main(): app = ConfWizApp() app.MainLoop() - if __name__ == '__main__': main() diff --git a/windows/pkgreshook.py b/windows/pkgreshook.py deleted file mode 100644 index bb1d985c..00000000 --- a/windows/pkgreshook.py +++ /dev/null @@ -1,46 +0,0 @@ - -def install(): - """ - This installs a hook into setuptools' pkg_resources infrastructure, so that resource - files can be found in files relative to the runnin executable, in addition to the - usual egg and source lookup mechanisms. This overrides the ZipProvider, since that - is the lookup mechanism triggered within pkg_resources when running code out of a - py2exe or py2app build's library.zip. - """ - import os, sys - import pkg_resources, zipimport - - platform_libdirs = { - 'darwin': '../Resources/pkg_resources', - } - exedir = os.path.dirname(sys.executable) - libdir = platform_libdirs.get(sys.platform, 'pkg_resources') - - class Provider(pkg_resources.ZipProvider): - - def __init__(self, module): - self._module_name = module.__name__ - pkg_resources.ZipProvider.__init__(self, module) - - def get_resource_filename(self, manager, resource_name): - #print 'get_resource_filename(%s, %s)' % (manager, resource_name) - path = [exedir, libdir] + self._module_name.split('.') + [resource_name] - localfile = os.path.join(*path) - #print ' checking(%s)' % (localfile,) - if os.path.exists(localfile): - #print 'found locally' - return localfile - else: - try: - ret = pkg_resources.ZipProvider.get_resource_filename(self, manager, resource_name) - #print 'returning %s' % (ret,) - return ret - except NotImplementedError: - #print 'get_resource_filename(%s,%s): not found' % (self._module_name, resource_name) - #import traceback - #traceback.print_exc() - return '' - - pkg_resources.register_loader_type(zipimport.zipimporter, Provider) - - diff --git a/windows/tahoe.py b/windows/tahoe.py index 50dd05c7..38dd1a78 100644 --- a/windows/tahoe.py +++ b/windows/tahoe.py @@ -1,5 +1,5 @@ -import pkgreshook # override the pkg_resources zip provider for py2exe deployment -pkgreshook.install() # this is done before nevow is imported by depends +from allmydata.util import pkgresutil # override the pkg_resources zip provider for py2exe deployment +pkgresutil.install() # this is done before nevow is imported by depends import depends # import dependencies so that py2exe finds them _junk = depends # appease pyflakes diff --git a/windows/tahoesvc.py b/windows/tahoesvc.py index f5db9d23..a2b5392a 100644 --- a/windows/tahoesvc.py +++ b/windows/tahoesvc.py @@ -22,8 +22,8 @@ logmsg('service loaded') # # Now with some bootstrap util functions in place, let's try and init things: try: - import pkgreshook # override the pkg_resources zip provider for py2exe deployment - pkgreshook.install() # this is done before nevow is imported + from allmydata.util import pkgresutil # override pkg_resources zip provider for py2exe deployment + pkgresutil.install() # this is done before nevow is imported logmsg('loading base dir') from allmydata.windows import registry