commit 5940999a49af50ff49aeabb1103543889c598312
Author: Arturo Filastò <arturo(a)filasto.net>
Date: Mon May 30 15:24:07 2016 +0200
Fix privilege shedding and daemonisation of oonibackend (#80)
* Fix privilege shedding and daemonisation of oonibackend
* Rewrite to use twistd
* Launch tor only after we have forked
* Set the UID of when starting tor
This fixes #65
* Add gitignore files and remove empty.txt files
* Drop support for super old versions of txtorcon
* Remove now unnecessary hacks to maintain backward compatibility
* Fix permissions on temporary tor data directory
---
bin/oonib | 38 ++-----
data/archive/.gitignore | 2 +
data/archive/empty.txt | 2 -
data/decks/.gitignore | 3 +
data/inputs/.gitignore | 3 +
data/reports/.gitignore | 2 +
data/tor/.gitignore | 2 +
data/tor/empty.txt | 2 -
oonib.conf.example | 4 -
oonib/config.py | 2 +
oonib/log.py | 61 +----------
oonib/onion.py | 63 +++++------
oonib/oonibackend.py | 280 ++++++++++++++++++++++++++----------------------
requirements.txt | 2 +-
setup.py | 6 +-
15 files changed, 213 insertions(+), 259 deletions(-)
diff --git a/bin/oonib b/bin/oonib
index 109c74e..ccbe246 100755
--- a/bin/oonib
+++ b/bin/oonib
@@ -2,55 +2,35 @@
import sys
import os
-from twisted.python import log, usage
-from twisted.internet import reactor
-from twisted.application import app
# Hack to set the proper sys.path. Overcomes the export PYTHONPATH pain.
sys.path[:] = map(os.path.abspath, sys.path)
sys.path.insert(0, os.path.abspath(os.getcwd()))
-from oonib import errors as e
+from oonib import errors
from oonib.config import config
-from oonib.log import LoggerFactory
-
try:
config.load()
-except e.ConfigFileNotSpecified:
+except errors.ConfigFileNotSpecified:
print "Config file not specified!"
print "Use -c to specify one!"
config.usageOptions()
sys.exit(1)
-except e.ConfigFileDoesNotExist, path:
+except errors.ConfigFileDoesNotExist, path:
print "Config file \"%s\" does not exist!" % path
sys.exit(2)
-except e.InvalidReportDirectory, path:
+except errors.InvalidReportDirectory, path:
print "Invalid report directory: %s!" % path
sys.exit(3)
-except e.InvalidArchiveDirectory, path:
+except errors.InvalidArchiveDirectory, path:
print "Invalid archive directory: %s!" % path
sys.exit(4)
-except e.InvalidInputDirectory, path:
+except errors.InvalidInputDirectory, path:
print "Invalid input directory: %s" % path
sys.exit(5)
-except e.InvalidDeckDirectory, path:
+except errors.InvalidDeckDirectory, path:
print "Invalid deck directory: %s" % path
sys.exit(6)
-if config.main.chroot:
- sys.argv.append('--chroot')
- sys.argv.append(config.chroot)
-
-if not config.main.nodaemon:
- sys.argv.append('-y')
-
-from oonib.oonibackend import application
-
-from twisted.scripts._twistd_unix import UnixApplicationRunner
-class OBaseRunner(UnixApplicationRunner):
- temporary_data_dir = None
- def createOrGetApplication(self):
- return application
-
-OBaseRunner.loggerFactory = LoggerFactory
-OBaseRunner(config.main).run()
+from oonib import oonibackend
+oonibackend.start()
diff --git a/data/archive/.gitignore b/data/archive/.gitignore
new file mode 100644
index 0000000..d6b7ef3
--- /dev/null
+++ b/data/archive/.gitignore
@@ -0,0 +1,2 @@
+*
+!.gitignore
diff --git a/data/archive/empty.txt b/data/archive/empty.txt
deleted file mode 100644
index 9a166f9..0000000
--- a/data/archive/empty.txt
+++ /dev/null
@@ -1,2 +0,0 @@
-In here will end up the archived reports.
-This file may be deleted at any time.
diff --git a/data/decks/.gitignore b/data/decks/.gitignore
new file mode 100644
index 0000000..514e47a
--- /dev/null
+++ b/data/decks/.gitignore
@@ -0,0 +1,3 @@
+*
+!.gitignore
+!README
diff --git a/data/inputs/.gitignore b/data/inputs/.gitignore
new file mode 100644
index 0000000..a0991ff
--- /dev/null
+++ b/data/inputs/.gitignore
@@ -0,0 +1,3 @@
+*
+!.gitignore
+!Makefile
diff --git a/data/reports/.gitignore b/data/reports/.gitignore
new file mode 100644
index 0000000..d6b7ef3
--- /dev/null
+++ b/data/reports/.gitignore
@@ -0,0 +1,2 @@
+*
+!.gitignore
diff --git a/data/tor/.gitignore b/data/tor/.gitignore
new file mode 100644
index 0000000..d6b7ef3
--- /dev/null
+++ b/data/tor/.gitignore
@@ -0,0 +1,2 @@
+*
+!.gitignore
diff --git a/data/tor/empty.txt b/data/tor/empty.txt
deleted file mode 100644
index ec3be8f..0000000
--- a/data/tor/empty.txt
+++ /dev/null
@@ -1,2 +0,0 @@
-In here will end up all tor related files.
-This file may be deleted at any time.
diff --git a/oonib.conf.example b/oonib.conf.example
index 6f4c7f3..bcf8393 100644
--- a/oonib.conf.example
+++ b/oonib.conf.example
@@ -7,8 +7,6 @@ main:
bouncer_file: data/bouncer.yaml
logfile: null
- database_uri: 'sqlite://oonib_test_db.db'
- db_threadpool_size: 10
tor_binary: null
socks_port: 9055
tor2webmode: false
@@ -21,9 +19,7 @@ main:
euid: null
uid: null
gid: null
- uuid: null
no_save: true
- profile: null
debug: false
stale_time: 3600
diff --git a/oonib/config.py b/oonib/config.py
index 31128a9..be29ec1 100644
--- a/oonib/config.py
+++ b/oonib/config.py
@@ -28,6 +28,8 @@ class Config(object):
raise e.ConfigFileDoesNotExist(config_file)
self.main = Storage(configuration['main'].items())
+ if self.main.logfile is None:
+ self.main.logfile = 'oonib.log'
self.helpers = Storage()
for name, helper in configuration['helpers'].items():
diff --git a/oonib/log.py b/oonib/log.py
index a79199e..c229f35 100644
--- a/oonib/log.py
+++ b/oonib/log.py
@@ -6,18 +6,14 @@
Twisted logger for the ooni backend system.
"""
-import os
import sys
import codecs
import logging
import traceback
from twisted.python import log as txlog
-from twisted.python import util
from twisted.python.failure import Failure
-from twisted.python.logfile import DailyLogFile
-from oonib import otime
from oonib.config import config
# Get rid of the annoying "No route found for
@@ -47,56 +43,21 @@ def log_encode(logmsg):
repr(logmsg)))
-class LogWithNoPrefix(txlog.FileLogObserver):
- def emit(self, eventDict):
- text = txlog.textFromEventDict(eventDict)
- if text is None:
- return
-
- util.untilConcludes(self.write, "%s\n" % text)
- util.untilConcludes(self.flush) # Hoorj!
-
-
-def start(application_name="oonib"):
- daily_logfile = None
-
- if not config.main.logfile:
- logfile = 'oonib.log'
- else:
- logfile = config.main.logfile
-
- log_folder = os.path.dirname(logfile)
- log_filename = os.path.basename(logfile)
-
- daily_logfile = DailyLogFile(log_filename, log_folder)
-
- txlog.msg("Starting %s on %s (%s UTC)" % (application_name,
- otime.prettyDateNow(),
- otime.utcPrettyDateNow()))
- txlog.msg("oonib version %s" % config.backend_version)
- txlog.startLoggingWithObserver(LogWithNoPrefix(sys.stdout).emit)
- txlog.addObserver(txlog.FileLogObserver(daily_logfile).emit)
-
-
-def stop():
- print "Stopping OONI"
-
-
def msg(msg, *arg, **kw):
- print "%s" % log_encode(msg)
+ txlog.msg("%s" % log_encode(msg))
def debug(msg, *arg, **kw):
if config.main.get('debug'):
- print "[D] %s" % log_encode(msg)
+ txlog.msg("[D] %s" % log_encode(msg))
def warn(msg, *arg, **kw):
- print "[W] %s" % log_encode(msg)
+ txlog.msg("[W] %s" % log_encode(msg))
def err(msg, *arg, **kw):
- print "[!] %s" % log_encode(msg)
+ txlog.err("[!] %s" % log_encode(msg))
def exception(error):
@@ -109,17 +70,3 @@ def exception(error):
else:
exc_type, exc_value, exc_traceback = sys.exc_info()
traceback.print_exception(exc_type, exc_value, exc_traceback)
-
-
-class LoggerFactory(object):
- """
- This is a logger factory to be used by oonib
- """
- def __init__(self, options):
- pass
-
- def start(self, application):
- start("OONIB")
-
- def stop(self):
- txlog.msg("Stopping OONIB")
diff --git a/oonib/onion.py b/oonib/onion.py
index 0a7a155..9a5c2c3 100644
--- a/oonib/onion.py
+++ b/oonib/onion.py
@@ -1,31 +1,17 @@
+import pwd
import tempfile
+
from oonib import log
from oonib.config import config
-from twisted.internet import reactor, endpoints, defer
+from twisted.internet import defer
import os
from random import randint
import socket
-from txtorcon import TCPHiddenServiceEndpoint, TorConfig
+from txtorcon import TorConfig
from txtorcon import launch_tor
-from txtorcon import __version__ as txtorcon_version
-if tuple(map(int, txtorcon_version.split('.'))) < (0, 9, 0):
- """
- Fix for bug in txtorcon versions < 0.9.0 where TCPHiddenServiceEndpoint
- listens on all interfaces by default.
- """
- def create_listener(self, proto):
- self._update_onion(self.hiddenservice.dir)
- self.tcp_endpoint = endpoints.TCP4ServerEndpoint(self.reactor,
- self.listen_port,
- interface='127.0.0.1')
- d = self.tcp_endpoint.listen(self.protocolfactory)
- d.addCallback(self._add_attributes).addErrback(self._retry_local_port)
- return d
- TCPHiddenServiceEndpoint._create_listener = create_listener
-
def randomFreePort(addr="127.0.0.1"):
"""
Args:
@@ -56,11 +42,15 @@ def txSetupFailed(failure):
def _configTor():
torconfig = TorConfig()
- if config.main.socks_port:
- torconfig.SocksPort = config.main.socks_port
- if config.main.control_port:
- torconfig.ControlPort = config.main.control_port
- if config.main.tor2webmode:
+ if config.main.socks_port is None:
+ config.main.socks_port = int(randomFreePort())
+ torconfig.SocksPort = config.main.socks_port
+
+ if config.main.control_port is None:
+ config.main.control_port = int(randomFreePort())
+ torconfig.ControlPort = config.main.control_port
+
+ if config.main.tor2webmode is True:
torconfig.Tor2webMode = 1
torconfig.CircuitBuildTimeout = 60
if config.main.tor_datadir is None:
@@ -68,26 +58,29 @@ def _configTor():
log.warn("Option 'tor_datadir' in oonib.conf is unspecified!")
log.warn("Using %s" % temporary_data_dir)
torconfig.DataDirectory = temporary_data_dir
+ uid = -1
+ gid = -1
+ if config.main.uid is not None:
+ uid = config.main.uid
+ if config.main.gid is not None:
+ gid = config.main.gid
+ os.chown(temporary_data_dir, uid, gid)
else:
if os.path.exists(config.main.tor_datadir):
torconfig.DataDirectory = os.path.abspath(config.main.tor_datadir)
else:
raise Exception("Could not find tor datadir")
+ if config.main.uid is not None:
+ try:
+ user = pwd.getpwuid(config.main.uid)[0]
+ except KeyError:
+ raise Exception("Invalid user ID")
+ torconfig.User = user
+
tor_log_file = os.path.join(torconfig.DataDirectory, "tor.log")
torconfig.Log = ["notice stdout", "notice file %s" % tor_log_file]
torconfig.save()
- if not hasattr(torconfig, 'ControlPort'):
- control_port = int(randomFreePort())
- torconfig.ControlPort = control_port
- config.main.control_port = control_port
-
- if not hasattr(torconfig, 'SocksPort'):
- socks_port = int(randomFreePort())
- torconfig.SocksPort = socks_port
- config.main.socks_port = socks_port
-
- torconfig.save()
return torconfig
# get_global_tor is a near-rip of that from txtorcon (so you can have some
@@ -110,7 +103,7 @@ def get_global_tor(reactor):
# start Tor launching
def updates(prog, tag, summary):
- print("%d%%: %s" % (prog, summary))
+ log.msg("%d%%: %s" % (prog, summary))
yield launch_tor(_global_tor_config, reactor,
progress_updates=updates,
tor_binary=config.main.tor_binary)
diff --git a/oonib/oonibackend.py b/oonib/oonibackend.py
index ebf3c52..a57bf92 100644
--- a/oonib/oonibackend.py
+++ b/oonib/oonibackend.py
@@ -7,7 +7,9 @@
# In here we start all the test helpers that are required by ooniprobe and
# start the report collector
-from distutils.version import LooseVersion
+import os
+import sys
+
from oonib.api import ooniBackend, ooniBouncer
from oonib.config import config
@@ -15,107 +17,22 @@ from oonib.onion import get_global_tor
from oonib.testhelpers import dns_helpers, ssl_helpers
from oonib.testhelpers import http_helpers, tcp_helpers
-import os
-
+from twisted.scripts import twistd
+from twisted.python import usage
from twisted.application import internet, service
-from twisted.internet import reactor, endpoints, ssl, defer
+from twisted.internet import reactor, endpoints, ssl
from twisted.names import dns
-from txtorcon import TCPHiddenServiceEndpoint, TorConfig
-from txtorcon import __version__ as txtorcon_version
-
-if config.main.uid and config.main.gid:
- application = service.Application('oonibackend', uid=config.main.uid,
- gid=config.main.gid)
-else:
- application = service.Application('oonibackend')
-
-multiService = service.MultiService()
-
-if config.helpers['ssl'].port:
- print "Starting SSL helper on %s" % config.helpers['ssl'].port
- ssl_helper = internet.SSLServer(int(config.helpers['ssl'].port),
- http_helpers.HTTPReturnJSONHeadersHelper(),
- ssl_helpers.SSLContext(config))
- multiService.addService(ssl_helper)
- ssl_helper.startService()
-
-# Start the DNS Server related services
-if config.helpers['dns'].tcp_port:
- print "Starting TCP DNS Helper on %s" % config.helpers['dns'].tcp_port
- tcp_dns_helper = internet.TCPServer(int(config.helpers['dns'].tcp_port),
- dns_helpers.DNSTestHelper())
- multiService.addService(tcp_dns_helper)
- tcp_dns_helper.startService()
-
-if config.helpers['dns'].udp_port:
- print "Starting UDP DNS Helper on %s" % config.helpers['dns'].udp_port
- udp_dns_factory = dns.DNSDatagramProtocol(dns_helpers.DNSTestHelper())
- udp_dns_helper = internet.UDPServer(int(config.helpers['dns'].udp_port),
- udp_dns_factory)
- multiService.addService(udp_dns_helper)
- udp_dns_helper.startService()
-
-if config.helpers['dns_discovery'].udp_port:
- print ("Starting UDP DNS Discovery Helper on %s" %
- config.helpers['dns_discovery'].udp_port)
- udp_dns_discovery = internet.UDPServer(
- int(config.helpers['dns_discovery'].udp_port),
- dns.DNSDatagramProtocol(dns_helpers.DNSResolverDiscovery())
- )
- multiService.addService(udp_dns_discovery)
-
-if config.helpers['dns_discovery'].tcp_port:
- print ("Starting TCP DNS Discovery Helper on %s" %
- config.helpers['dns_discovery'].tcp_port)
- tcp_dns_discovery = internet.TCPServer(
- int(config.helpers['dns_discovery'].tcp_port),
- dns_helpers.DNSResolverDiscovery()
- )
- multiService.addService(tcp_dns_discovery)
- tcp_dns_discovery.startService()
-
-
-# XXX this needs to be ported
-# Start the OONI daphn3 backend
-if config.helpers['daphn3'].port:
- print "Starting Daphn3 helper on %s" % config.helpers['daphn3'].port
- daphn3_helper = internet.TCPServer(int(config.helpers['daphn3'].port),
- tcp_helpers.Daphn3Server())
- multiService.addService(daphn3_helper)
- daphn3_helper.startService()
-
-
-if config.helpers['tcp-echo'].port:
- print "Starting TCP echo helper on %s" % config.helpers['tcp-echo'].port
- tcp_echo_helper = internet.TCPServer(int(config.helpers['tcp-echo'].port),
- tcp_helpers.TCPEchoHelper())
- multiService.addService(tcp_echo_helper)
- tcp_echo_helper.startService()
-
-if config.helpers['http-return-json-headers'].port:
- print ("Starting HTTP return request helper on %s" %
- config.helpers['http-return-json-headers'].port)
- http_return_request_helper = internet.TCPServer(
- int(config.helpers['http-return-json-headers'].port),
- http_helpers.HTTPReturnJSONHeadersHelper())
- multiService.addService(http_return_request_helper)
- http_return_request_helper.startService()
def getHSEndpoint(endpoint_config):
+ from txtorcon import TCPHiddenServiceEndpoint
hsdir = endpoint_config['hsdir']
hsdir = os.path.expanduser(hsdir)
hsdir = os.path.realpath(hsdir)
- if LooseVersion(txtorcon_version) >= LooseVersion('0.10.0'):
- return TCPHiddenServiceEndpoint(reactor,
- get_global_tor(reactor),
- 80,
- hidden_service_dir=hsdir)
- else:
- return TCPHiddenServiceEndpoint(reactor,
- get_global_tor(reactor),
- 80,
- data_dir=hsdir)
+ return TCPHiddenServiceEndpoint(reactor,
+ config=get_global_tor(reactor),
+ public_port=80,
+ hidden_service_dir=hsdir)
def getTCPEndpoint(endpoint_config):
return endpoints.TCP4ServerEndpoint(
@@ -159,35 +76,146 @@ def createService(endpoint, role, endpoint_config):
endpoint, factory
)
service.setName("-".join([endpoint_config['type'], role]))
- multiService.addService(service)
- service.startService()
-
-# this is to ensure same behaviour with an old config file
-if config.main.tor_hidden_service and \
- config.main.bouncer_endpoints is None and \
- config.main.collector_endpoints is None:
- base_dir = '.'
- if config.main.tor_datadir is not None:
- base_dir = config.main.tor_datadir
- bouncer_hsdir = os.path.join(base_dir, 'bouncer')
- collector_hsdir = os.path.join(base_dir, 'collector')
- config.main.bouncer_endpoints = [ {'type': 'onion', 'hsdir': bouncer_hsdir} ]
- config.main.collector_endpoints = [ {'type': 'onion', 'hsdir': collector_hsdir} ]
-
-for endpoint_config in config.main.get('bouncer_endpoints', []):
- if config.main.bouncer_file:
- print "Starting bouncer with config %s" % endpoint_config
- endpoint = getEndpoint(endpoint_config)
- createService(endpoint, 'bouncer', endpoint_config)
- else:
- print "No bouncer configured"
-
-for endpoint_config in config.main.get('collector_endpoints', []):
- print "Starting collector with config %s" % endpoint_config
- endpoint = getEndpoint(endpoint_config)
- createService(endpoint, 'collector', endpoint_config)
-
-for endpoint_config in config.helpers.web_connectivity.get('endpoints', []):
- print "Starting web_connectivity helper with config %s" % endpoint_config
- endpoint = getEndpoint(endpoint_config)
- createService(endpoint, 'web_connectivity', endpoint_config)
+ return service
+
+class StartOONIBackendPlugin:
+ tapname = "oonibackend"
+ def makeService(self, so):
+ ooniBackendService = service.MultiService()
+
+ if config.helpers['ssl'].port:
+ print "Starting SSL helper on %s" % config.helpers['ssl'].port
+ ssl_helper = internet.SSLServer(int(config.helpers['ssl'].port),
+ http_helpers.HTTPReturnJSONHeadersHelper(),
+ ssl_helpers.SSLContext(config))
+ ooniBackendService.addService(ssl_helper)
+
+ # Start the DNS Server related services
+ if config.helpers['dns'].tcp_port:
+ print "Starting TCP DNS Helper on %s" % config.helpers['dns'].tcp_port
+ tcp_dns_helper = internet.TCPServer(int(config.helpers['dns'].tcp_port),
+ dns_helpers.DNSTestHelper())
+ ooniBackendService.addService(tcp_dns_helper)
+
+ if config.helpers['dns'].udp_port:
+ print "Starting UDP DNS Helper on %s" % config.helpers['dns'].udp_port
+ udp_dns_factory = dns.DNSDatagramProtocol(dns_helpers.DNSTestHelper())
+ udp_dns_helper = internet.UDPServer(int(config.helpers['dns'].udp_port),
+ udp_dns_factory)
+ ooniBackendService.addService(udp_dns_helper)
+
+ if config.helpers['dns_discovery'].udp_port:
+ print ("Starting UDP DNS Discovery Helper on %s" %
+ config.helpers['dns_discovery'].udp_port)
+ udp_dns_discovery = internet.UDPServer(
+ int(config.helpers['dns_discovery'].udp_port),
+ dns.DNSDatagramProtocol(dns_helpers.DNSResolverDiscovery())
+ )
+ ooniBackendService.addService(udp_dns_discovery)
+
+ if config.helpers['dns_discovery'].tcp_port:
+ print ("Starting TCP DNS Discovery Helper on %s" %
+ config.helpers['dns_discovery'].tcp_port)
+ tcp_dns_discovery = internet.TCPServer(
+ int(config.helpers['dns_discovery'].tcp_port),
+ dns_helpers.DNSResolverDiscovery()
+ )
+ ooniBackendService.addService(tcp_dns_discovery)
+
+ # XXX this needs to be ported
+ # Start the OONI daphn3 backend
+ if config.helpers['daphn3'].port:
+ print "Starting Daphn3 helper on %s" % config.helpers['daphn3'].port
+ daphn3_helper = internet.TCPServer(int(config.helpers['daphn3'].port),
+ tcp_helpers.Daphn3Server())
+ ooniBackendService.addService(daphn3_helper)
+
+ if config.helpers['tcp-echo'].port:
+ print "Starting TCP echo helper on %s" % config.helpers['tcp-echo'].port
+ tcp_echo_helper = internet.TCPServer(int(config.helpers['tcp-echo'].port),
+ tcp_helpers.TCPEchoHelper())
+ ooniBackendService.addService(tcp_echo_helper)
+
+ if config.helpers['http-return-json-headers'].port:
+ print ("Starting HTTP return request helper on %s" %
+ config.helpers['http-return-json-headers'].port)
+ http_return_request_helper = internet.TCPServer(
+ int(config.helpers['http-return-json-headers'].port),
+ http_helpers.HTTPReturnJSONHeadersHelper())
+ ooniBackendService.addService(http_return_request_helper)
+
+ # this is to ensure same behaviour with an old config file
+ if config.main.tor_hidden_service and \
+ config.main.bouncer_endpoints is None and \
+ config.main.collector_endpoints is None:
+ bouncer_hsdir = os.path.join(config.main.tor_datadir, 'bouncer')
+ collector_hsdir = os.path.join(config.main.tor_datadir, 'collector')
+ config.main.bouncer_endpoints = [ {'type': 'onion', 'hsdir': bouncer_hsdir} ]
+ config.main.collector_endpoints = [ {'type': 'onion', 'hsdir': collector_hsdir} ]
+
+ for endpoint_config in config.main.get('bouncer_endpoints', []):
+ if config.main.bouncer_file:
+ print "Starting bouncer with config %s" % endpoint_config
+ endpoint = getEndpoint(endpoint_config)
+ bouncer_service = createService(endpoint, 'bouncer',
+ endpoint_config)
+ ooniBackendService.addService(bouncer_service)
+ else:
+ print "No bouncer configured"
+
+ for endpoint_config in config.main.get('collector_endpoints', []):
+ print "Starting collector with config %s" % endpoint_config
+ endpoint = getEndpoint(endpoint_config)
+ collector_service = createService(endpoint, 'collector',
+ endpoint_config)
+ ooniBackendService.addService(collector_service)
+
+ for endpoint_config in config.helpers.web_connectivity.get('endpoints', []):
+ print "Starting web_connectivity helper with config %s" % endpoint_config
+ endpoint = getEndpoint(endpoint_config)
+ web_connectivity_service = createService(endpoint,
+ 'web_connectivity',
+ endpoint_config)
+ ooniBackendService.addService(web_connectivity_service)
+
+
+ return ooniBackendService
+
+class OONIBackendTwistdConfig(twistd.ServerOptions):
+ subCommands = [("StartOONIBackend", None, usage.Options, "node")]
+
+def start():
+ twistd_args = []
+
+ flags = [
+ 'nodaemon',
+ 'no_save'
+ ]
+ options = [
+ 'pidfile',
+ 'logfile',
+ 'rundir',
+ 'euid',
+ 'gid',
+ 'uid',
+ 'umask'
+ ]
+ for option in options:
+ if config.main.get(option, None) is not None:
+ twistd_args.append('--%s' % option)
+ twistd_args.append(config.main.get(option))
+ for flag in flags:
+ if config.main.get(flag, None) is True:
+ twistd_args.append('--%s'% flag)
+
+ twistd_args.append('StartOONIBackend') # Point to our backend plugin
+ twistd_config = OONIBackendTwistdConfig()
+ try:
+ twistd_config.parseOptions(twistd_args)
+ except usage.error, ue:
+ print "Usage error from twistd"
+ sys.exit(7)
+
+ twistd_config.loadedPlugins = {'StartOONIBackend': StartOONIBackendPlugin()}
+ twistd.runApp(twistd_config)
+ return 0
diff --git a/requirements.txt b/requirements.txt
index b8c18a8..91a711a 100644
--- a/requirements.txt
+++ b/requirements.txt
@@ -6,7 +6,7 @@ Twisted>=13.2.0
cyclone>=1.1
ipaddr>=2.1.10
pygeoip>=0.2.6
-txtorcon>=0.7
+txtorcon>=0.11.0
pyOpenSSL>=0.13
zope.component>=4.0.0
zope.event>=4.0.0
diff --git a/setup.py b/setup.py
index 2113d21..39cb1f9 100644
--- a/setup.py
+++ b/setup.py
@@ -67,9 +67,9 @@ data_files = [
(data_dir, ['oonib.conf.example']),
(os.path.join(data_dir, 'decks'), ['data/decks/README']),
(os.path.join(data_dir, 'inputs'), ['data/inputs/Makefile']),
- (os.path.join(spool_dir, 'reports'), ['data/reports/empty.txt']),
- (os.path.join(spool_dir, 'archive'), ['data/archive/empty.txt']),
- (os.path.join(var_dir, 'tor'), ['data/tor/empty.txt']),
+ (os.path.join(spool_dir, 'reports'), ['data/reports/.gitignore']),
+ (os.path.join(spool_dir, 'archive'), ['data/archive/.gitignore']),
+ (os.path.join(var_dir, 'tor'), ['data/tor/.gitignore']),
(var_dir, ['data/bouncer.yaml', 'data/policy.yaml'])
]