#!/usr/bin/env python3
# coding:utf-8

import os
import sys

current_path = os.path.dirname(os.path.abspath(__file__))
helper_path = os.path.abspath(os.path.join(current_path, os.pardir, os.pardir, os.pardir, 'data', 'launcher', 'helper'))

if __name__ == "__main__":
    default_path = os.path.abspath(os.path.join(current_path, os.pardir))
    noarch_lib = os.path.abspath(os.path.join(default_path, 'lib', 'noarch'))
    sys.path.append(noarch_lib)
    osx_lib = os.path.join(default_path, 'lib', 'darwin')
    sys.path.append(osx_lib)
    extra_lib = "/System/Library/Frameworks/Python.framework/Versions/3.8/Extras/lib/python/PyObjC"
    sys.path.append(extra_lib)

from config import config
import module_init
import subprocess
import webbrowser

from xlog import getLogger
xlog = getLogger("launcher")

import AppKit
import SystemConfiguration
from PyObjCTools import AppHelper


class MacTrayObject(AppKit.NSObject):
    def __init__(self):
        pass

    def applicationDidFinishLaunching_(self, notification):
        setupHelper()
        loadConfig()
        self.setupUI()
        self.registerObserver()

    def setupUI(self):
        self.statusbar = AppKit.NSStatusBar.systemStatusBar()
        self.statusitem = self.statusbar.statusItemWithLength_(
            AppKit.NSSquareStatusItemLength)  # NSSquareStatusItemLength #NSVariableStatusItemLength

        # Set initial image icon
        icon_path = os.path.join(current_path, "web_ui", "favicon-mac.ico")
        image = AppKit.NSImage.alloc().initByReferencingFile_(icon_path)
        image.setScalesWhenResized_(True)
        image.setSize_((20, 20))
        self.statusitem.setImage_(image)

        # Let it highlight upon clicking
        self.statusitem.setHighlightMode_(1)
        self.statusitem.setToolTip_("XX-Net")

        # Get current selected mode
        proxyState = getProxyState(currentService)

        # Build a very simple menu
        self.menu = AppKit.NSMenu.alloc().initWithTitle_('XX-Net')

        menuitem = AppKit.NSMenuItem.alloc().initWithTitle_action_keyEquivalent_('Config', 'config:', '')
        self.menu.addItem_(menuitem)

        menuitem = AppKit.NSMenuItem.alloc().initWithTitle_action_keyEquivalent_(getCurrentServiceMenuItemTitle(), None, '')
        self.menu.addItem_(menuitem)
        self.currentServiceMenuItem = menuitem

        menuitem = AppKit.NSMenuItem.alloc().initWithTitle_action_keyEquivalent_('Enable Auto GAEProxy',
                                                                                 'enableAutoProxy:', '')
        if proxyState == 'pac':
            menuitem.setState_(AppKit.NSOnState)
        self.menu.addItem_(menuitem)
        self.autoGaeProxyMenuItem = menuitem

        menuitem = AppKit.NSMenuItem.alloc().initWithTitle_action_keyEquivalent_('Enable Global GAEProxy',
                                                                                 'enableGlobalProxy:', '')
        if proxyState == 'gae':
            menuitem.setState_(AppKit.NSOnState)
        self.menu.addItem_(menuitem)
        self.globalGaeProxyMenuItem = menuitem

        menuitem = AppKit.NSMenuItem.alloc().initWithTitle_action_keyEquivalent_('Enable Global X-Tunnel',
                                                                                 'enableGlobalXTunnel:', '')
        if proxyState == 'x_tunnel':
            menuitem.setState_(AppKit.NSOnState)
        self.menu.addItem_(menuitem)
        self.globalXTunnelMenuItem = menuitem

        menuitem = AppKit.NSMenuItem.alloc().initWithTitle_action_keyEquivalent_('Enable Global Smart-Router',
                                                                                 'enableGlobalSmartRouter:', '')
        if proxyState == 'smart_router':
            menuitem.setState_(AppKit.NSOnState)
        self.menu.addItem_(menuitem)
        self.globalSmartRouterMenuItem = menuitem

        menuitem = AppKit.NSMenuItem.alloc().initWithTitle_action_keyEquivalent_('Disable GAEProxy', 'disableProxy:',
                                                                                 '')
        if proxyState == 'disable':
            menuitem.setState_(AppKit.NSOnState)
        self.menu.addItem_(menuitem)
        self.disableGaeProxyMenuItem = menuitem

        # Reset Menu Item
        menuitem = AppKit.NSMenuItem.alloc().initWithTitle_action_keyEquivalent_('Reset Each Module',
                                                                                 'restartEachModule:', '')
        self.menu.addItem_(menuitem)
        # Default event
        menuitem = AppKit.NSMenuItem.alloc().initWithTitle_action_keyEquivalent_('Quit', 'windowWillClose:', '')
        self.menu.addItem_(menuitem)
        # Bind it to the status item
        self.statusitem.setMenu_(self.menu)

        # Hide dock icon
        AppKit.NSApp.setActivationPolicy_(AppKit.NSApplicationActivationPolicyProhibited)

    def updateStatusBarMenu(self):
        self.currentServiceMenuItem.setTitle_(getCurrentServiceMenuItemTitle())

        # Remove Tick before All Menu Items
        self.autoGaeProxyMenuItem.setState_(AppKit.NSOffState)
        self.globalGaeProxyMenuItem.setState_(AppKit.NSOffState)
        self.globalXTunnelMenuItem.setState_(AppKit.NSOffState)
        self.globalSmartRouterMenuItem.setState_(AppKit.NSOffState)
        self.disableGaeProxyMenuItem.setState_(AppKit.NSOffState)

        # Get current selected mode
        proxyState = getProxyState(currentService)

        # Update Tick before Menu Item
        if proxyState == 'pac':
            self.autoGaeProxyMenuItem.setState_(AppKit.NSOnState)
        elif proxyState == 'gae':
            self.globalGaeProxyMenuItem.setState_(AppKit.NSOnState)
        elif proxyState == 'x_tunnel':
            self.globalXTunnelMenuItem.setState
_(AppKit.NSOnState)
        elif proxyState == 'smart_router':
            self.globalSmartRouterMenuItem.setState_(AppKit.NSOnState)
        elif proxyState == 'disable':
            self.disableGaeProxyMenuItem.setState_(AppKit.NSOnState)

     
   # Trigger autovalidation
        self.menu.update()

    def validateMenuItem_(self, menuItem):
        return currentService or (menuItem != self.autoGaeProxyMenuItem and
                                  menuItem != self.globalGaeProxyMenuItem and
                                  menuItem != self.globalXTunnelMenuItem and
                                  menuItem != self.globalSmartRouterMenuItem and
                                  menuItem != self.disableGaeProxyMenuItem)

    def presentAlert_withTitle_(self, msg, title):
        self.performSelectorOnMainThread_withObject_waitUntilDone_('presentAlertWithInfo:', [title, msg], True)
        return self.alertReturn

    def presentAlertWithInfo_(self, info):
        alert = AppKit.NSAlert.alloc().init()
        alert.setMessageText_(info[0])
        alert.setInformativeText_(info[1])
        alert.addButtonWithTitle_("OK")
        alert.addButtonWithTitle_("Cancel")
        self.alertReturn = alert.runModal() == AppKit.NSAlertFirstButtonReturn

    def registerObserver(self):
        nc = AppKit.NSWorkspace.sharedWorkspace().notificationCenter()
        nc.addObserver_selector_name_object_(self, 'windowWillClose:', AppKit.NSWorkspaceWillPowerOffNotification, None)

    def windowWillClose_(self, notification):
        executeResult = subprocess.check_output(['networksetup', '-listallnetworkservices'])
        services = executeResult.split(b'\n')
        services = [service for service in services if service and service.find(b'*') == -1 and getProxyState(
            service) != 'disable']  # Remove disabled services and empty lines

        if len(services) > 0:
            try:
                list(map(helperDisableAutoProxy, services))
                list(map(helperDisableGlobalProxy, services))
            except:
                disableAutoProxyCommand = ';'.join(map(getDisableAutoProxyCommand, services))
                disableGlobalProxyCommand = ';'.join(map(getDisableGlobalProxyCommand, services))
                executeCommand = 'do shell script "%s;%s" with administrator privileges' % (
                disableAutoPr