Skip to content

Instantly share code, notes, and snippets.

@redxef
Created July 20, 2018 10:26
Show Gist options
  • Save redxef/62453be1524b98c88deb39388843bf90 to your computer and use it in GitHub Desktop.
Save redxef/62453be1524b98c88deb39388843bf90 to your computer and use it in GitHub Desktop.
Switches between a tor network service in macOS and other services, while simultaniously starting tor.
#!/usr/bin/env python3
import sys
import subprocess
import getopt
import shlex
import time
# known issues:
# 1: When a service is inactive in the networking prefs, then this script
# failes.
def get_network_service_order(debug=False):
cmd = [
'bash',
'-c',
'networksetup -listnetworkserviceorder'
+ ' | grep "([0-9][0-9]*)"'
+ ' | sed "s/([0-9][0-9]*) //"',
]
comp = subprocess.run(cmd, stdout=subprocess.PIPE, encoding='utf-8')
res = comp.stdout.split('\n')
res = [x for x in res if len(x) != 0]
return res
def get_tor_network_service_name(debug=False):
for name in get_network_service_order():
name_lower = name.lower()
if 'tor' in name_lower:
return name
def set_network_service_order(nets, debug=False):
cmd = [
'bash',
'-c',
'networksetup -ordernetworkservices'
+ ' ' + ' '.join(['"' + x + '"' for x in nets]),
]
subprocess.run(cmd)
def get_tor_pid(debug=False):
cmd = [
'bash',
'-c',
'ps -ax | grep \ tor.*$ | grep -v grep | grep -o " *[0-9][0-9]*" | head -n1',
]
comp = subprocess.run(cmd, stdout=subprocess.PIPE, encoding='utf-8')
if debug:
subprocess.run(cmd[0:2] + ['ps -ax | grep \ tor\.*$ | grep -v grep'], encoding='utf-8')
pid = comp.stdout.strip()
if len(pid) == 0:
return None
return int(pid)
def start_tor(args=[], reorder=True, debug=False):
if get_tor_pid() == None:
print('starting tor...')
if debug:
so = sys.stdout
se = sys.stderr
print('args: ' + str(args))
else:
so = subprocess.DEVNULL
se = subprocess.DEVNULL
subprocess.Popen(
['tor'] + args,
stdout=so,
stderr=se,
close_fds=True
)
else:
print('tor already running')
if reorder:
tor = get_tor_network_service_name()
servs = get_network_service_order()
pservs = servs.copy()
servs.remove(tor)
servs = [tor] + servs
if servs == pservs:
print('tor network service is already the active one.')
else:
print('setting service', tor, 'as the active one...')
set_network_service_order(servs)
def stop_tor(reorder=True, debug=False):
pid = get_tor_pid()
if pid == None:
print('there is no tor process running')
else:
print('stopping tor process...')
subprocess.run(
['kill', str(pid)],
stdout=subprocess.DEVNULL,
stderr=subprocess.DEVNULL
)
if reorder:
tor = get_tor_network_service_name()
servs = get_network_service_order()
if servs[0] == tor:
print('making tor service inactive...')
servs = servs[1:] + [tor]
set_network_service_order(servs)
else:
print('currently active service is not the tor service, skipping...')
def main():
start = False
stop = False
restart = False
debug = False
status = False
args = sys.argv[1:]
if len(args) == 0:
args = ['-t']
options, args = getopt.gnu_getopt(
args, 'sStrhda:',
['start', 'stop', 'toggle',
'restart', 'status', 'help',
'debug', 'args='],
)
args = []
for o, a in options:
if len(o) == 2:
o = o[1:]
else:
o = o[2:]
if o in ['s', 'start']:
start = True
elif o in ['S', 'stop']:
stop = True
elif o in ['t', 'toggle']:
if get_tor_pid() == None:
start = True
else:
stop = True
elif o in ['r', 'restart']:
restart = True
elif o in ['h', 'help']:
pass
elif o in ['d', 'debug']:
debug = True
elif o in ['a', 'args']:
args = shlex.split(a)
elif o in ['status']:
status = True
if start:
start_tor(args=args, debug=debug)
if stop:
stop_tor(debug=debug)
if restart:
if get_tor_pid(debug=debug) == None:
print("nothing to restart, starting...")
start_tor(args=args, debug=debug)
else:
stop_tor(reorder=False, debug=debug)
start_tor(args=args, reorder=True, debug=debug)
if status:
if stop:
time.sleep(1)
if get_tor_pid(debug=debug) == None:
print("tor inactive")
else:
print("tor active")
servs = get_network_service_order(debug=debug)
tor = get_tor_network_service_name(debug=debug)
if servs[0] == tor:
print("tor service active")
else:
print("tor service inactive")
if __name__ == '__main__':
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment