diff --git a/LICENSE b/LICENSE index 530ff5739d86e1808d85b7987045e4ca3f87b284..bbc331e47f5facbe49113980b79630b0b350543f 100644 --- a/LICENSE +++ b/LICENSE @@ -1,6 +1,6 @@ GetTor is distributed under this license: -Copyright (c) 2008-2014, The Tor Project, Inc. +Copyright (c) 2008-2020, The Tor Project, Inc. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are @@ -28,4 +28,4 @@ LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. \ No newline at end of file +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/MANIFEST.in b/MANIFEST.in deleted file mode 100644 index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..0000000000000000000000000000000000000000 diff --git a/doc/UPLOAD-DROPBOX b/doc/UPLOAD-DROPBOX deleted file mode 100644 index dc0728ad2c39d1ad485c97cf7fe80e2ca25a64b5..0000000000000000000000000000000000000000 --- a/doc/UPLOAD-DROPBOX +++ /dev/null @@ -1,20 +0,0 @@ -1) Get the current repo: - -$ git clone https://github.com/ileiva/gettor.git - -2) Check if you have Dropbox and GnuPG Python modules. If not, install them: - -$ pip install dropbox gnupg - -4) Get the PGP key that signs the Tor Browser Bundles. - -3) Change general configuration and account info in dropbox.cfg. - -3) Run the script: - -$ python dropbox.py - -If everything works fine, you should see a dropbox.links file inside the -'providers' directory. The script will take the files on upload_dir -(dropbox.cfg) that end up on .xz and .xz.asc respectively. A script for -getting the latest bundles from dist.tp.o is pending. \ No newline at end of file diff --git a/doc/UPLOAD-GOOGLE-DRIVE b/doc/UPLOAD-GOOGLE-DRIVE deleted file mode 100644 index 0ab505e994c345f5856bd8136f3c7c67bc8e222c..0000000000000000000000000000000000000000 --- a/doc/UPLOAD-GOOGLE-DRIVE +++ /dev/null @@ -1,21 +0,0 @@ -1) Clone into the latest version of gettor: - -$ git clone https://github.com/ilv/gettor.git - -2) Get the PGP key that signs the Tor Browser Bundle - -2) Visit https://console.developers.google.com//start/api?id=drive&credential=client_key and follow OAUTH2 process to get client ID and client secret for 'other' desktop application. - -3) Edit drive.cfg to with new client-id and secret. Leave refresh_token empty. - -4) Install the google drive API python client: - -$ pip install --upgrade google-api-python-client - -5) Run the script: - -$ python bundles2drive.py - -The first time the script is run, you will have to authorize it through a web browser. You will be prompted with a URL. Once that is done, a refresh token will be stored locally so that re-authorzing is unnesaccary. - -The script will then look for files in upload_dir (as specified in drive.cfg) and upload them to google drive. If no errors occur, it will then add formatted links and hash information to the drive.links file. diff --git a/gettor/web/http.py b/gettor/web/http.py deleted file mode 100644 index 2801db094f46ed8b061a2e4e8962e172f6014265..0000000000000000000000000000000000000000 --- a/gettor/web/http.py +++ /dev/null @@ -1,491 +0,0 @@ -# -*- coding: utf-8 -*- -# -# This file is part of GetTor. -# -# :authors: Israel Leiva -# see also AUTHORS file -# -# :copyright: (c) 2008-2015, The Tor Project, Inc. -# (c) 2015, Israel Leiva -# -# :license: This is Free Software. See LICENSE for license information. - -import os -import re -import json -import codecs -import urllib2 -import configparser - -from time import gmtime, strftime - -import core - -""" -GetTor RESTful API -This part of GetTor has not been integrated into twisted-gettor just yet. -""" - -# currently supported locales for Tor Browser -LC = ['ar', 'de', 'en-US', 'es-ES', 'fa', 'fr', 'it', 'ko', 'nl', 'pl', - 'pt-PT', 'ru', 'tr', 'vi', 'zh-CN'] - -# https://gitweb.tpo/tor-browser-spec.git/tree/processes/VersionNumbers -# does not say anything about operating systems, so it's possible the -# notation might change in the future. We should always use the same three -# strings though: linux, windows, osx. -OS = { - 'Linux': 'linux', - 'Windows': 'windows', - 'MacOS': 'osx' -} - -# based on -# https://gitweb.tpo.org/tor-browser-spec.git/tree/processes/VersionNumbers -# except for the first one, which is based on current RecommendedTBBVersions -RE = { - 'os': '(.*)-(\w+)', - 'alpha': '\d\.\d(\.\d)*a\d+', - 'stable': '\d\.\d(\.\d)*' -} - -# strings to build names of packages depending on OS. -PKG = { - 'windows': 'torbrowser-install-%s_%s.exe', - 'linux': 'tor-browser-linux%s-%s_%s.tar.xz', - 'osx': 'TorBrowser-%s-osx64_%s.dmg' -} - -# bin and asc are used to build the download links for each version, os and lc -URL = { - 'version': 'https://www.torproject.org/projects/torbrowser/RecommendedTBBVersions', - 'bin': 'https://www.torproject.org/dist/torbrowser/%s/%s', - 'asc': 'https://www.torproject.org/dist/torbrowser/%s/%s.asc' -} - - - -class ConfigError(Exception): - pass - - -class InternalError(Exception): - pass - - -class HTTP(object): - """ Provide useful resources via RESTful API. """ - def __init__(self, cfg=None): - """ Create new object by reading a configuration file. - - :param: cfg (string) path of the configuration file. - - """ - default_cfg = 'http.cfg' - config = ConfigParser.ConfigParser() - - if cfg is None or not os.path.isfile(cfg): - cfg = default_cfg - - try: - with open(cfg) as f: - config.readfp(f) - except IOError: - raise ConfigError("File %s not found!" % cfg) - - try: - # path to static tree of API - self.tree = config.get('general', 'tree') - # server that provides the RESTful API - self.server = config.get('general', 'url') - # path to the links files - self.links_path = config.get('general', 'links') - # path to mirrors in json - self.mirrors_path = config.get('general', 'mirrors') - - # we will ask gettor.core for the links - core_cfg = config.get('general', 'core') - self.core = core.Core(core_cfg) - - except ConfigParser.Error as e: - raise ConfigError("Configuration error: %s" % str(e)) - except core.ConfigError as e: - raise InternalError("HTTP error: %s" % str(e)) - - def _is_json(self, my_json): - """ Check if json generated is valid. - - :param: my_json (string) data to ve verified. - - :return: (bool) true if data is json-valid, false otherwise. - - """ - try: - json_object = json.loads(my_json) - except ValueError, e: - return False - return True - - def _write_json(self, path, content): - """ - """ - try: - with codecs.open( - path, - "w", - "utf-8" - ) as jsonfile: - # Make pretty json - json.dump( - content, - jsonfile, - sort_keys=True, - indent=4, - separators=(',', ': '), - encoding="utf-8", - ) - except IOError as e: - #logging.error("Couldn't write json: %s" % str(e)) - print "Error building %s: %s" % (path, str(e)) - print "%s built" % path - - def _get_provider_name(self, p): - """ Return simplified version of provider's name. - - :param: p (string) provider's name. - - :return: (string) provider's name in lowercase and without spaces. - - """ - p = p.replace(' ', '-') - return p.lower() - - def _add_links(self, lv, release, version, os): - """ Add link for all locales in LC depending on given OS. - - :param: lv (dict) latest version data structure. - :param: release (string) release to which add the links. - :param: version (string) version obtained from tpo. - :param: os (string) operating system. - - """ - for lc in LC: - if os == 'linux': - pkg32 = PKG['linux'] % ('32', version, lc) - link_bin32 = URL['bin'] % (version, pkg32) - link_asc32 = URL['asc'] % (version, pkg32) - - pkg64 = PKG['linux'] % ('64', version, lc) - link_bin64 = URL['bin'] % (version, pkg64) - link_asc64 = URL['asc'] % (version, pkg64) - - lv[release]['downloads'][os][lc] = { - 'binary32': link_bin32, - 'signature32': link_asc32, - 'binary64': link_bin64, - 'signature64': link_asc64, - } - else: - if os == 'windows': - pkg = PKG['windows'] % (version, lc) - - elif os == 'osx': - pkg = PKG['osx'] % (version, lc) - - else: - continue - - link_bin = URL['bin'] % (version, pkg) - link_asc = URL['asc'] % (version, pkg) - lv[release]['downloads'][os][lc] = { - 'binary': link_bin, - 'signature': link_asc - } - - def _load_latest_version(self): - """ Load latest version data. """ - response = urllib2.urlopen(URL['version']) - json_response = json.load(response) - - lv = { - 'stable': { - 'latest_version': '', - 'downloads': {} - }, - 'alpha': { - 'latest_version': '', - 'downloads': {} - } - } - - self.releases = { - 'alpha': '%s/latest/alpha' % self.server, - 'stable': '%s/latest/stable' % self.server, - 'updated_at': strftime("%Y-%m-%d %H:%M:%S", gmtime()) - } - - # one iteration to find the latest version for each release - for v in json_response: - # latest version for each release - if not re.match(RE['os'], v): - if re.match(RE['alpha'], v): - if v > lv['alpha']['latest_version']: - # we'll use the latest one - lv['alpha']['latest_version'] = v - - elif re.match(RE['stable'], v): - if v > lv['stable']['latest_version']: - # we'll use the latest one - lv['stable']['latest_version'] = v - - latest_alpha = lv['alpha']['latest_version'] - latest_stable = lv['stable']['latest_version'] - - # another iteration to add the links - for v in json_response: - # based on current RecommendedTBBVersions scheme - # for each release and for each os we build links for all locales - if re.match(RE['os'], v): - m = re.match(RE['os'], v) - version = m.group(1) - osys = m.group(2) - - if osys in OS: - if latest_alpha and version == latest_alpha \ - and re.match(RE['alpha'], version): - lv['alpha']['downloads'][OS[osys]] = {} - self._add_links(lv, 'alpha', version, OS[osys]) - - elif latest_stable and version == latest_stable \ - and re.match(RE['stable'], version): - lv['stable']['downloads'][OS[osys]] = {} - self._add_links(lv, 'stable', version, OS[osys]) - - lv['updated_at'] = strftime("%Y-%m-%d %H:%M:%S", gmtime()) - self.lv = lv - - def _load_links(self): - """ Load links and providers data. """ - links_files = [] - - # look for files ending with .links in links_path - p = re.compile('.*\.links$') - for name in os.listdir(self.links_path): - path = os.path.abspath(os.path.join(self.links_path, name)) - if os.path.isfile(path) and p.match(path): - links_files.append(path) - - links = {} - providers = {} - supported_os = self.core.get_supported_os() - supported_lc = self.core.get_supported_lc() - - for name in links_files: - config = ConfigParser.ConfigParser() - try: - with open(name) as f: - config.readfp(f) - except IOError: - raise InternalError("File %s not found!" % name) - - try: - pname = config.get('provider', 'name') - pname = self._get_provider_name(pname) - - # build providers dict - providers[pname] = '%s/providers/%s' % (self.server, pname) - providers['updated_at'] = strftime( - "%Y-%m-%d %H:%M:%S", gmtime() - ) - - self.providers = providers - links[pname] = {} - - # build links data. - for osys in supported_os: - links[pname][osys] = {} - for lc in supported_lc: - links[pname][osys][lc] = {} - - for osys in supported_os: - for lc in supported_lc: - l_str = config.get(osys, lc) - - # linux has 32 and 64 bit packages - if osys == 'linux': - l32_str, l64_str = l_str.split(',') - - link32, sig32, sha32 = [ - l for l in l32_str.split("$") if l - ] - - link64, sig64, sha64 = [ - l for l in l64_str.split("$") if l - ] - link64 = link64.lstrip() - - links[pname][osys][lc]['binary32'] = link32 - links[pname][osys][lc]['signature32'] = sig32 - links[pname][osys][lc]['sha256-32'] = sha32 - links[pname][osys][lc]['binary64'] = link64 - links[pname][osys][lc]['signature64'] = sig64 - links[pname][osys][lc]['sha256-64'] = sha64 - - else: - link, sig, sha = [l for l in l_str.split("$") if l] - links[pname][osys][lc]['binary'] = link - links[pname][osys][lc]['signature'] = sig - links[pname][osys][lc]['sha256'] = sha - - except ConfigParser.Error as e: - raise InternalError("%s" % str(e)) - - links['updated_at'] = strftime("%Y-%m-%d %H:%M:%S", gmtime()) - self.links = links - - def _load_mirrors(self): - """ Load mirrors data. """ - mirrors = [] - - # json of mirrors should be obtained from get_mirrors.py - json_data = open(self.mirrors_path).read() - mirrors = json.loads(json_data) - - self.mirrors = mirrors - - def _load_resources(self): - """ Load available resources data. """ - - self.resources = { - 'providers': '%s/providers' % self.server, - 'mirrors': '%s/mirrors' % self.server, - 'latest_version': '%s/latest' % self.server, - 'updated_at': strftime("%Y-%m-%d %H:%M:%S", gmtime()) - } - - def load_data(self): - """ Load all data. - - Since data is not frequently updated, we load all data before - running the RESTful API. Every time the links/mirrors/version - data is updated we should restart the API. - - """ - self._load_links() - self._load_mirrors() - self._load_resources() - self._load_latest_version() - - def build(self): - """ Build RESTful API. """ - - print "Building API" - - # resources - self._write_json( - os.path.join(self.tree, 'api'), - self.resources - ) - - api_path = os.path.join(self.tree, 'api-content') - if not os.path.isdir(api_path): - os.mkdir(api_path) - - # providers - self._write_json( - os.path.join(api_path, 'providers'), - self.providers - ) - - providers_path = os.path.join(api_path, 'providers-content') - if not os.path.isdir(providers_path): - os.mkdir(providers_path) - - for provider in self.links: - if provider == 'updated_at': - continue - - self._write_json( - os.path.join(providers_path, provider), - self.links[provider] - ) - - provider_path = os.path.join( - providers_path, - "%s-content" % provider - ) - - if not os.path.isdir(provider_path): - os.mkdir(provider_path) - - for osys in self.links[provider]: - self._write_json( - os.path.join(provider_path, osys), - self.links[provider][osys] - ) - - provider_os_path = os.path.join( - provider_path, "%s-content" % osys - ) - - if not os.path.isdir(provider_os_path): - os.mkdir(provider_os_path) - - for lc in self.links[provider][osys]: - self._write_json( - os.path.join(provider_os_path, lc), - self.links[provider][osys][lc] - ) - - # latest version - self._write_json( - os.path.join(api_path, 'latest'), - self.lv - ) - - lv_path = os.path.join(api_path, 'latest-content') - if not os.path.isdir(lv_path): - os.mkdir(lv_path) - - for release in self.lv: - if release == 'updated_at': - continue - - self._write_json( - os.path.join(lv_path, release), - self.lv[release] - ) - - release_path = os.path.join( - lv_path, - "%s-content" % release - ) - - if not os.path.isdir(release_path): - os.mkdir(release_path) - - for osys in self.lv[release]['downloads']: - self._write_json( - os.path.join(release_path, osys), - self.lv[release]['downloads'][osys] - ) - - release_os_path = os.path.join( - release_path, - "%s-content" % osys - ) - - if not os.path.isdir(release_os_path): - os.mkdir(release_os_path) - - for lc in self.lv[release]['downloads'][osys]: - self._write_json( - os.path.join(release_os_path, lc), - self.lv[release]['downloads'][osys][lc] - ) - - # mirrors - self._write_json( - os.path.join(api_path, 'mirrors'), - self.mirrors - ) diff --git a/strings.patch b/strings.patch deleted file mode 100644 index ea0504a42a73b3ee29f70cf80479d5c313a50ec1..0000000000000000000000000000000000000000 --- a/strings.patch +++ /dev/null @@ -1,301 +0,0 @@ -From 906bec40b28a7e49ffba3a6e1c646bd81e5441b9 Mon Sep 17 00:00:00 2001 -From: hiro -Date: Thu, 9 Jan 2020 12:24:10 +0100 -Subject: [PATCH] Fix current issue with gettor strings splitting #32906 Add - tests to check sent email messages. - ---- - gettor/services/email/sendmail.py | 82 ++++++++++++++++++------------- - gettor/utils/options.py | 8 +-- - gettor/utils/settings.py | 7 +-- - scripts/process_email | 6 ++- - share/locale/es.json | 2 +- - tests/conftests.py | 2 +- - tests/test_email_service.py | 35 ++++++++++++- - tests/test_twitter.py | 1 + - 8 files changed, 98 insertions(+), 45 deletions(-) - -diff --git a/gettor/services/email/sendmail.py b/gettor/services/email/sendmail.py -index 53d90f6..356f6c4 100644 ---- a/gettor/services/email/sendmail.py -+++ b/gettor/services/email/sendmail.py -@@ -100,6 +100,52 @@ class Sendmail(object): - ).addCallback(self.sendmail_callback).addErrback(self.sendmail_errback) - - -+ def build_help_body_message(self): -+ body_msg = strings._("help_body_intro") -+ body_msg += strings._("help_body_paragraph") -+ body_msg += strings._("help_body_support") -+ -+ return body_msg -+ -+ -+ def build_link_strings(self, links, platform, locale): -+ """ -+ Build the links strings -+ """ -+ -+ link_msg = None -+ -+ for link in links: -+ provider = link[5] -+ version = link[4] -+ arch = link[3] -+ url = link[0] -+ file = link[7] -+ sig_url = url + ".asc" -+ -+ link_str = "Tor Browser {} for {}-{}-{} ({}): {}\n".format( -+ version, platform, locale, arch, provider, url -+ ) -+ -+ link_str += "Signature file: {}\n".format(sig_url) -+ -+ link_msg = "{}\n{}".format(link_msg, link_str) -+ -+ return link_msg, file -+ -+ -+ def build_body_message(self, link_msg, platform, file): -+ body_msg = strings._("links_body_platform").format(platform) -+ body_msg += strings._("links_body_links").format(link_msg) -+ body_msg += strings._("links_body_archive") -+ body_msg += strings._("links_body_internet_archive") -+ body_msg += strings._("links_body_google_drive") -+ body_msg += strings._("links_body_internet_archive").format(file) -+ body_msg += strings._("links_body_ending") -+ -+ return body_msg -+ -+ - @defer.inlineCallbacks - def get_new(self): - """ -@@ -132,9 +178,7 @@ class Sendmail(object): - ) - ) - -- body_msg = strings._("help_body_intro") -- body_msg += strings._("help_body_paragraph") -- body_msg += strings._("help_body_support") -+ body_msg = self.build_help_body_message() - - yield self.sendmail( - email_addr=id, -@@ -179,36 +223,8 @@ class Sendmail(object): - ) - - # build message -- link_msg = None -- file = "" -- -- for link in links: -- provider = link[5] -- version = link[4] -- arch = link[3] -- url = link[0] -- file = link[7] -- sig_url = url + ".asc" -- -- link_str = "Tor Browser {} for {}-{}-{} ({}): {}\n".format( -- version, platform, locale, arch, provider, url -- ) -- -- link_str += "Signature file: {}\n".format(sig_url) -- -- if link_msg: -- link_msg = "{}\n{}".format(link_msg, link_str) -- else: -- link_msg = link_str -- -- body_msg = strings._("links_body_platform").format(platform) -- body_msg += strings._("links_body_links").format(link_msg) -- body_msg += strings._("links_body_archive") -- body_msg += strings._("links_body_internet_archive") -- body_msg += strings._("links_body_google_drive") -- body_msg += strings._("links_body_internet_archive").format(file) -- body_msg += strings._("links_body_ending") -- -+ link_msg, file = self.build_link_strings(links, platform, locale) -+ body_msg = self.build_body_message(link_msg, platform, file) - subject_msg = strings._("links_subject") - - hid = hashlib.sha256(id.encode('utf-8')) -diff --git a/gettor/utils/options.py b/gettor/utils/options.py -index 8504f42..6f8d693 100644 ---- a/gettor/utils/options.py -+++ b/gettor/utils/options.py -@@ -3,9 +3,7 @@ - This file is part of GetTor, a service providing alternative methods to download - the Tor Browser. - --:authors: Hiro -- parser = argparse.ArgumentParser(formatter_class=lambda prog: argparse.HelpFormatter(prog,max_help_position=28)) -- parser.add_argument('--config', metavar='config', please also see AUTHORS file -+:authors: Hiro please also see AUTHORS file - :copyright: (c) 2008-2014, The Tor Project, Inc. - (c) 2014, all entities within the AUTHORS file - :license: see included LICENSE for information -@@ -24,11 +22,13 @@ def load_settings(config): - settings.load() - return settings - --def parse_settings(locale, config): -+def parse_settings(locale="en", config=None): - """ - Parse settings and loads strings in a given locale - This function needs to be rewritten considering passing a locale and - returing translated strings -+ - """ -+ - strings.load_strings(locale) - return load_settings(config) -diff --git a/gettor/utils/settings.py b/gettor/utils/settings.py -index a519755..67c31ec 100644 ---- a/gettor/utils/settings.py -+++ b/gettor/utils/settings.py -@@ -33,7 +33,8 @@ class Settings(object): - self.filename = config - else: - # Default config -- self.filename = self.build_filename() -+ default_config = "/home/gettor/gettor/gettor.conf.json" -+ self.filename = self.build_filename(default_config) - - # Dictionary of available languages, - # mapped to the language name, in that language -@@ -41,11 +42,11 @@ class Settings(object): - self._version = strings.get_version() - self._settings = {} - -- def build_filename(self): -+ def build_filename(self, file): - """ - Returns the path of the settings file. - """ -- return strings.get_resource_path('/home/gettor/gettor/gettor.conf.json', strings.find_run_dir()) -+ return strings.get_resource_path(file, strings.find_run_dir()) - - def load(self): - """ -diff --git a/scripts/process_email b/scripts/process_email -index a5da6eb..37c4e0b 100755 ---- a/scripts/process_email -+++ b/scripts/process_email -@@ -23,7 +23,8 @@ from gettor.utils import options - - @defer.inlineCallbacks - def process_email(message): -- settings = options.parse_settings() -+ -+ settings = options.parse_settings("en", "/home/gettor/gettor/gettor.conf.json") - - try: - ep = EmailParser(settings, "gettor@torproject.org") -@@ -49,7 +50,8 @@ def main(): - - - if __name__ == '__main__': -- settings = options.parse_settings() -+ -+ settings = options.parse_settings("en", "/home/gettor/gettor/gettor.conf.json") - email_parser_logfile = settings.get("email_parser_logfile") - log.startLogging(open(email_parser_logfile, 'a')) - log.msg("New email request received.", system="process email") -diff --git a/share/locale/es.json b/share/locale/es.json -index be7dd33..8ac5705 100644 ---- a/share/locale/es.json -+++ b/share/locale/es.json -@@ -15,7 +15,7 @@ - "help_config": "Custom config file location (optional)", - "smtp_links_subject": "[GetTor] Links for your request", - "smtp_mirrors_subject": "[GetTor] Mirrors", -- "smtp_help_subject": "[GetTor] Help", -+ "smtp_help_subject": "[GetTor] Ayuda", - "smtp_unsupported_locale_subject": "[GetTor] Unsupported locale", - "smtp_unsupported_locale_msg": "The locale you requested '{}' is not supported." - } -diff --git a/tests/conftests.py b/tests/conftests.py -index f5194a5..cbb4d28 100644 ---- a/tests/conftests.py -+++ b/tests/conftests.py -@@ -5,7 +5,7 @@ from __future__ import unicode_literals - from gettor.utils import options - from gettor.utils import strings - from gettor.utils import twitter --from gettor.services.email import sendmail -+from gettor.services.email.sendmail import Sendmail - from gettor.services.twitter import twitterdm - from gettor.parse.email import EmailParser, AddressError, DKIMError - from gettor.parse.twitter import TwitterParser -diff --git a/tests/test_email_service.py b/tests/test_email_service.py -index 8e60f7a..ff364f0 100644 ---- a/tests/test_email_service.py -+++ b/tests/test_email_service.py -@@ -14,8 +14,20 @@ class EmailServiceTests(unittest.TestCase): - timeout = 15 - def setUp(self): - self.settings = conftests.options.parse_settings("en","./gettor.conf.json") -- self.sm_client = conftests.sendmail.Sendmail(self.settings) -+ self.sm_client = conftests.Sendmail(self.settings) - self.locales = conftests.strings.get_locales() -+ self.links = [ -+ [ -+ "https://gitlab.com/thetorproject/gettorbrowser/raw/torbrowser-releases/TorBrowser-9.0.3-osx64_en-US.dmg", -+ "osx", -+ "en-US", -+ "64", -+ "9.0.3", -+ "gitlab", -+ "ACTIVE", -+ "TorBrowser-9.0.3-osx64_en-US.dmg" -+ ] -+ ] - - def tearDown(self): - print("tearDown()") -@@ -76,6 +88,27 @@ class EmailServiceTests(unittest.TestCase): - self.assertEqual(request["platform"], "osx") - self.assertEqual(request["language"], "en") - -+ def test_sent_links_message(self): -+ ep = self.sm_client -+ links = self.links -+ link_msg, file = ep.build_link_strings(links, "osx", "en") -+ assert "https://gitlab.com/thetorproject/gettorbrowser/raw/torbrowser-releases/TorBrowser-9.0.3-osx64_en-US.dmg" in link_msg -+ assert "osx" in link_msg -+ -+ self.assertEqual("TorBrowser-9.0.3-osx64_en-US.dmg", file) -+ -+ def test_sent_body_message(self): -+ ep = self.sm_client -+ links = self.links -+ link_msg, file = ep.build_link_strings(links, "osx", "en") -+ body_msg = ep.build_body_message(link_msg, "osx", file) -+ assert "You requested Tor Browser for osx" in body_msg -+ -+ def test_help_body_message(self): -+ ep = self.sm_client -+ help_msg = ep.build_help_body_message() -+ assert "This is how you can request a tor browser bundle link" in help_msg -+ - - if __name__ == "__main__": - unittest.main() -diff --git a/tests/test_twitter.py b/tests/test_twitter.py -index 7458cfc..a1515d0 100644 ---- a/tests/test_twitter.py -+++ b/tests/test_twitter.py -@@ -20,6 +20,7 @@ class TwitterTests(unittest.TestCase): - - def test_load_messages(self): - data = self.tw_client.twitter_data() -+ print(data) - assert data['events'] - - --- -2.20.1 - diff --git a/upload/bundles2drive.py b/upload/bundles2drive.py deleted file mode 100644 index 0acada5d62bb3245d0c57e47a21bd7f8733084af..0000000000000000000000000000000000000000 --- a/upload/bundles2drive.py +++ /dev/null @@ -1,315 +0,0 @@ -# -*- coding: utf-8 -*- -# -# This file is part of GetTor, a Tor Browser distribution system. -# -# :authors: poly -# Israel Leiva -# see also AUTHORS file -# -# :copyright: (c) 2008-2014, The Tor Project, Inc. -# (c) 2014, Poly -# (c) 2014, Israel Leiva -# -# :license: This is Free Software. See LICENSE for license information. - -import re -import os -import gnupg -import hashlib -import logging -import argparse -import ConfigParser -import gettor.core -from gettor.utils import get_bundle_info, get_file_sha256, valid_format - -# import google drive libs -import httplib2 -from apiclient.discovery import build -from apiclient.http import MediaFileUpload -from apiclient import errors -from oauth2client.client import FlowExchangeError -from oauth2client.client import OAuth2WebServerFlow -from oauth2client.client import Credentials - - -def upload_files(client, basedir): - """Upload files to Google Drive. - - Looks for tor browser files inside basedir. - - :param: basedir (string) path of the folder with the files to be - uploaded. - :param: client (object) Google Drive object. - - :raise: UploadError if something goes wrong while uploading the - files to Google Drive. All files are uploaded to '/'. - - :return: (dict) the names of the uploaded files as the keys, - and file id as the value - - """ - files = [] - - for name in os.listdir(basedir): - path = os.path.abspath(os.path.join(basedir, name)) - if os.path.isfile(path) and valid_format(name, 'linux'): - files.append(name) - - for name in os.listdir(basedir): - path = os.path.abspath(os.path.join(basedir, name)) - if os.path.isfile(path) and valid_format(name, 'windows'): - files.append(name) - - for name in os.listdir(basedir): - path = os.path.abspath(os.path.join(basedir, name)) - if os.path.isfile(path) and valid_format(name, 'osx'): - files.append(name) - - # dictionary to store file names and IDs - files_dict = dict() - - for file in files: - asc = "%s.asc" % file - abs_file = os.path.abspath(os.path.join(basedir, file)) - abs_asc = os.path.abspath(os.path.join(basedir, asc)) - - if not os.path.isfile(abs_asc): - # there are some .mar files that don't have .asc, don't upload it - continue - - # upload tor browser installer - file_body = MediaFileUpload( - abs_file, - mimetype="application/octet-stream", - resumable=True - ) - body = { - 'title': file - } - print "Uploading '%s'..." % file - try: - file_data = drive_service.files().insert( - body=body, - media_body=file_body - ).execute() - except errors.HttpError, e: - print str(e) - - # upload signature - asc_body = MediaFileUpload(abs_asc, resumable=True) - asc_head = { - 'title': "%s.asc" % file - } - print "Uploading '%s'..." % asc - try: - asc_data = drive_service.files().insert( - body=asc_head, - media_body=asc_body - ).execute() - except errors.HttpError, e: - print str(e) - - # add filenames and file id to dict - files_dict[file] = file_data['id'] - files_dict[asc] = asc_data['id'] - - return files_dict - - -def share_file(service, file_id): - """Make files public - - For a given file-id, sets role 'reader' to 'anyone'. Returns public - link to file. - - :param: file_id (string) - - :return: (string) url to shared file - - """ - permission = { - 'type': "anyone", - 'role': "reader", - 'withLink': True - } - - try: - service.permissions().insert( - fileId=file_id, - body=permission - ).execute() - except errors.HttpError, error: - print('An error occured while sharing: %s' % file_id) - - try: - file = service.files().get(fileId=file_id).execute() - except errors.HttpError, error: - print('Error occured while fetch public link for file: %s' % file_id) - - print "Uploaded %s to %s" % (file['title'], file['webContentLink']) - return file['webContentLink'] - - -def get_files_links(service, v): - """Print links of uploaded files. - - :param: service (object): Goolge Drive service object. - :param: v (string): Version of Tor Browser to look for. - - """ - - windows_re = 'torbrowser-install-%s_\w\w(-\w\w)?\.exe(\.asc)?' % v - linux_re = 'tor-browser-linux\d\d-%s_(\w\w)(-\w\w)?\.tar\.xz(\.asc)?' % v - osx_re = 'TorBrowser-%s-osx\d\d_(\w\w)(-\w\w)?\.dmg(\.asc)?' % v - - # dictionary to store file names and IDs - files_dict = dict() - - print "Trying to fetch links of uploaded files..." - links = service.files().list().execute() - items = links.get('items', []) - - if not items: - raise ValueError('No files found.') - - else: - for item in items: - if re.search(windows_re, item['title']): - files_dict[item['title']] = item['id'] - elif re.search(linux_re, item['title']): - files_dict[item['title']] = item['id'] - elif re.search(osx_re, item['title']): - files_dict[item['title']] = item['id'] - return files_dict - -if __name__ == '__main__': - parser = argparse.ArgumentParser( - description='Utility to upload Tor Browser to Google Drive.' - ) - - # if no LC specified, download all - parser.add_argument( - '-l', '--links', default=None, - help='Create links file with files already uploaded and '\ - 'matching the specified version. ' - ) - - args = parser.parse_args() - - config = ConfigParser.ConfigParser() - config.read('drive.cfg') - - client_id = config.get('app', 'client-id') - app_secret = config.get('app', 'secret') - refresh_token = config.get('app', 'refresh_token') - upload_dir = config.get('general', 'upload_dir') - - # important: this key must be the one that signed the packages - tbb_key = config.get('general', 'tbb_key') - - # requests full access to drive account - OAUTH_SCOPE = 'https://www.googleapis.com/auth/drive' - REDIRECT_URI = 'urn:ietf:wg:oauth:2.0:oob' - - print "Authenticating..." - - flow = OAuth2WebServerFlow( - client_id, - app_secret, - OAUTH_SCOPE, - redirect_uri=REDIRECT_URI - ) - - # If no valid token found, need to prompt user. - # this should only occur once - if not refresh_token: - flow.params['access_type'] = 'offline' - flow.params['approval_prompt'] = 'force' - authorize_url = flow.step1_get_authorize_url() - print 'Go to the following link in your browser: ' + authorize_url - code = raw_input('Enter verification code: ').strip() - try: - credentials = flow.step2_exchange(code) - except FlowExchangeError as e: - print str(e) - - # oauth2 credentials instance must be stored as json string - config.set('app', 'refresh_token', credentials.to_json()) - with open('drive.cfg', 'wb') as configfile: - config.write(configfile) - else: - # we already have a valid token - credentials = Credentials.new_from_json(refresh_token) - - # authenticate with oauth2 - http = httplib2.Http() - http = credentials.authorize(http) - - # initialize drive instance - drive_service = build('drive', 'v2', http=http) - - # import key fingerprint - gpg = gnupg.GPG() - key_data = open(tbb_key).read() - import_result = gpg.import_keys(key_data) - fp = import_result.results[0]['fingerprint'] - - # make groups of four characters to make fingerprint more readable - # e.g. 123A 456B 789C 012D 345E 678F 901G 234H 567I 890J - readable = ' '.join(fp[i:i+4] for i in xrange(0, len(fp), 4)) - - try: - # helpful when something fails but files are uploaded. - if args.links: - uploaded_files = get_files_links(drive_service, args.links) - - if not uploaded_files: - raise ValueError("There are no files for that version") - else: - uploaded_files = upload_files(drive_service, upload_dir) - # use default config - core = gettor.core.Core('/home/gettor/core.cfg') - - # erase old links - core.create_links_file('Drive', readable) - - # recognize file OS by its extension - p1 = re.compile('.*\.tar.xz$') - p2 = re.compile('.*\.exe$') - p3 = re.compile('.*\.dmg$') - p4 = re.compile('.*\.asc$') - - for file in uploaded_files.keys(): - # only run for tor browser installers - if p4.match(file): - continue - asc = "%s.asc" % file - abs_file = os.path.abspath(os.path.join(upload_dir, file)) - abs_asc = os.path.abspath(os.path.join(upload_dir, asc)) - - sha_file = get_file_sha256(abs_file) - - # build links - link_file = share_file( - drive_service, - uploaded_files[file] - ) - - link_asc = share_file( - drive_service, - uploaded_files["%s.asc" % file] - ) - - if p1.match(file): - osys, arch, lc = get_bundle_info(file, 'linux') - elif p2.match(file): - osys, arch, lc = get_bundle_info(file, 'windows') - elif p3.match(file): - osys, arch, lc = get_bundle_info(file, 'osx') - - link = "%s$%s$%s$" % (link_file, link_asc, sha_file) - - # note that you should only upload bundles for supported locales - core.add_link('Drive', osys, lc, link) - except (ValueError, RuntimeError) as e: - print str(e) diff --git a/upload/bundles2dropbox.py b/upload/bundles2dropbox.py deleted file mode 100644 index 04e86af7383d8363419fcb6e9abfbe259c0088f3..0000000000000000000000000000000000000000 --- a/upload/bundles2dropbox.py +++ /dev/null @@ -1,150 +0,0 @@ -# -*- coding: utf-8 -*- -# -# This file is part of GetTor, a Tor Browser distribution system. -# -# :authors: Israel Leiva -# see also AUTHORS file -# -# :copyright: (c) 2008-2014, The Tor Project, Inc. -# (c) 2014, Israel Leiva -# -# :license: This is Free Software. See LICENSE for license information. - -import re -import os -import gnupg -import hashlib -import ConfigParser - -import dropbox -import gettor.core -from gettor.utils import get_bundle_info, get_file_sha256, valid_format - - -def upload_files(basedir, client): - """Upload files to Dropbox. - - Looks for files ending with 'tar.xz' inside basedir. - - :param: basedir (string) path of the folder with the files to be - uploaded. - :param: client (object) DropboxClient object. - - :raise: ValueError if the .xz file doesn't have an .asc file. - :raise: UploadError if something goes wrong while uploading the - files to Dropbox. All files are uploaded to '/'. - - :return: (list) the names of the uploaded files. - - """ - files = [] - - for name in os.listdir(basedir): - path = os.path.abspath(os.path.join(basedir, name)) - if os.path.isfile(path) and valid_format(name, 'linux'): - files.append(name) - - for name in os.listdir(basedir): - path = os.path.abspath(os.path.join(basedir, name)) - if os.path.isfile(path) and valid_format(name, 'windows'): - files.append(name) - - for name in os.listdir(basedir): - path = os.path.abspath(os.path.join(basedir, name)) - if os.path.isfile(path) and valid_format(name, 'osx'): - files.append(name) - - for file in files: - asc = "%s.asc" % file - abs_file = os.path.abspath(os.path.join(basedir, file)) - abs_asc = os.path.abspath(os.path.join(basedir, asc)) - - if not os.path.isfile(abs_asc): - # there are some .mar files that don't have .asc, don't upload it - continue - - # chunk upload for big files - to_upload = open(abs_file, 'rb') - size = os.path.getsize(abs_file) - uploader = client.get_chunked_uploader(to_upload, size) - while uploader.offset < size: - try: - upload = uploader.upload_chunked() - except dropbox.rest.ErrorResponse, e: - print("An error ocurred while uploading %s: %s" % abs_file, e) - uploader.finish(file) - print "Uploading %s" % file - - # this should be small, upload it simple - to_upload_asc = open(abs_asc, 'rb') - response = client.put_file(asc, to_upload_asc) - print "Uploading %s" % asc - - return files - -if __name__ == '__main__': - config = ConfigParser.ConfigParser() - config.read('dropbox.cfg') - - app_key = config.get('app', 'key') - app_secret = config.get('app', 'secret') - access_token = config.get('app', 'access_token') - upload_dir = config.get('general', 'upload_dir') - - # important: this key must be the one that signed the packages - tbb_key = config.get('general', 'tbb_key') - - client = dropbox.client.DropboxClient(access_token) - - # import key fingerprint - gpg = gnupg.GPG() - key_data = open(tbb_key).read() - import_result = gpg.import_keys(key_data) - fp = import_result.results[0]['fingerprint'] - - # make groups of four characters to make fingerprint more readable - # e.g. 123A 456B 789C 012D 345E 678F 901G 234H 567I 890J - readable = ' '.join(fp[i:i+4] for i in xrange(0, len(fp), 4)) - - try: - uploaded_files = upload_files(upload_dir, client) - # use default config - core = gettor.core.Core('/home/gettor/core.cfg') - - # erase old links - core.create_links_file('Dropbox', readable) - - # recognize file OS by its extension - p1 = re.compile('.*\.tar.xz$') - p2 = re.compile('.*\.exe$') - p3 = re.compile('.*\.dmg$') - - for file in uploaded_files: - # build file names - asc = "%s.asc" % file - abs_file = os.path.abspath(os.path.join(upload_dir, file)) - abs_asc = os.path.abspath(os.path.join(upload_dir, asc)) - - sha_file = get_file_sha256(abs_file) - - # build links - link_file = client.share(file, short_url=False) - # if someone finds how to do this with the API, please tell me! - link_file[u'url'] = link_file[u'url'].replace('?dl=0', '?dl=1') - link_asc = client.share(asc, short_url=False) - link_asc[u'url'] = link_asc[u'url'].replace('?dl=0', '?dl=1') - if p1.match(file): - osys, arch, lc = get_bundle_info(file, 'linux') - elif p2.match(file): - osys, arch, lc = get_bundle_info(file, 'windows') - elif p3.match(file): - osys, arch, lc = get_bundle_info(file, 'osx') - - link = "%s$%s$%s$" % (link_file[u'url'], link_asc[u'url'], sha_file) - - # note that you should only upload bundles for supported locales - core.add_link('Dropbox', osys, lc, link) - except (ValueError, RuntimeError) as e: - print str(e) - except dropbox.rest.ErrorResponse as e: - print str(e) diff --git a/upload/bundles2github.py b/upload/bundles2github.py deleted file mode 100644 index ee157f026c6bd3c9c3d9e88d4f8b78c14f0bce5a..0000000000000000000000000000000000000000 --- a/upload/bundles2github.py +++ /dev/null @@ -1,158 +0,0 @@ -# -*- coding: utf-8 -*- -# -# This file is part of GetTor, a Tor Browser distribution system. -# -# :authors: Israel Leiva -# see also AUTHORS file -# -# :copyright: (c) 2015, The Tor Project, Inc. -# (c) 2015, Israel Leiva -# -# :license: This is Free Software. See LICENSE for license information. -# - -# Use pyopenssl to verify TLS certifcates -try: - import urllib3.contrib.pyopenssl - urllib3.contrib.pyopenssl.inject_into_urllib3() -except ImportError: - pass - -import os -import sys -import argparse -import ConfigParser -import gnupg - -import github3 - -import gettor.core -from gettor.utils import (get_bundle_info, get_file_sha256, - find_files_to_upload) - - -def upload_new_release(github_repo, version, upload_dir): - """ - Returns a Release object - """ - - # Create a new release of this TBB - release = target_repo.create_release( - 'v{}'.format(version), - target_commitish="master", - name='Tor Browser {}'.format(version), - body='', - draft=True, - ) - - for filename in find_files_to_upload(upload_dir): - # Upload each file for this release - file_path = os.path.join(upload_dir, filename) - print("Uploading file {}".format(filename)) - release.upload_asset('application/zip', - filename, open(file_path, 'rb')) - - return release - - -if __name__ == '__main__': - parser = argparse.ArgumentParser( - description='Utility to upload Tor Browser to Github.' - ) - - # with this we only get the links of files already uploaded - # useful when somethings fail after uploading - parser.add_argument( - '-l', '--links', default=None, - help='Create links file with files already uploaded.' - ) - - args = parser.parse_args() - - config = ConfigParser.ConfigParser() - config.read('github.cfg') - - tbb_version_path = config.get('general', 'version_cfg_path') - - tbb_version_config = ConfigParser.ConfigParser() - tbb_version_config.read(tbb_version_path) - version = tbb_version_config.get('version', 'current') - - # the token allow us to run this script without GitHub user/pass - github_access_token = config.get('app', 'access_token') - - # path to the fingerprint that signed the packages - tb_key = config.get('general', 'tbb_key_path') - - # path to the latest version of Tor Browser - tb_path = config.get('general', 'latest_path') - - # path to gettor code configuration - core_path = config.get('general', 'core_path') - - # user and repository where we upload Tor Browser - github_user = config.get('app', 'user') - github_repo = config.get('app', 'repo') - - gh = github3.login(token=github_access_token) - target_repo = gh.repository(github_user, github_repo) - - # import key fingerprint - gpg = gnupg.GPG() - key_data = open(tb_key).read() - import_result = gpg.import_keys(key_data) - fp = import_result.results[0]['fingerprint'] - - # make groups of four characters to make fingerprint more readable - # e.g. 123A 456B 789C 012D 345E 678F 901G 234H 567I 890J - readable_fp = ' '.join(fp[i:i+4] for i in xrange(0, len(fp), 4)) - - # Find any published releases with this version number - for release in target_repo.releases(): - if release.tag_name == 'v{}'.format(version) and not release.draft: - print("Found an existing published release with this version. " - "Not uploading again unless you delete the published " - "release '{}'.".format(release.tag_name)) - break - else: - release = None - - if args.links or release: - # Only generating link file, should use previously published release - if not release: - print("Error occured! Could not find a published release for " - "version {}".format(version)) - sys.exit(1) - - else: - # Remove any drafts to clean broken uploads - print('Uploading release, please wait, this might take a while!') - # Upload the latest browser bundles to a new release - release = upload_new_release(target_repo, version, tb_path) - - # Upload success, publish the release - release.edit(draft=False) - - # Create the links file for this release - core = gettor.core.Core(core_path) - - # Erase old links if any and create a new empty one - core.create_links_file('GitHub', readable_fp) - - print("Creating links file") - for asset in release.assets(): - url = asset.browser_download_url - if url.endswith('.asc'): - continue - - osys, arch, lc = get_bundle_info(asset.name) - sha256 = get_file_sha256( - os.path.abspath(os.path.join(tb_path, asset.name)) - ) - - link = "{}${}${}$".format(url, url + ".asc", sha256) - - print("Adding {}".format(url)) - core.add_link('GitHub', osys, lc, link) - - print "Github links updated!" diff --git a/upload/drive.cfg b/upload/drive.cfg deleted file mode 100644 index a71bf57b43000088d36ee3163ccb9b92c37f824b..0000000000000000000000000000000000000000 --- a/upload/drive.cfg +++ /dev/null @@ -1,9 +0,0 @@ -[general] -upload_dir = latest -tbb_key = torbrowser-key.asc - -[app] -client-id = -secret = -refresh_token = - diff --git a/upload/dropbox.cfg b/upload/dropbox.cfg deleted file mode 100644 index 75285659133784efdce52465f35306c33ad08749..0000000000000000000000000000000000000000 --- a/upload/dropbox.cfg +++ /dev/null @@ -1,8 +0,0 @@ -[general] -upload_dir: latest -tbb_key: torbrowser-key.asc - -[app] -key: suchkey -secret: suchsecret -access_token: suchtoken diff --git a/upload/fetch_latest_torbrowser.py b/upload/fetch_latest_torbrowser.py deleted file mode 100644 index 3fe1f9a5a35b4ec72260bfc4c3b36a8ea204bb1c..0000000000000000000000000000000000000000 --- a/upload/fetch_latest_torbrowser.py +++ /dev/null @@ -1,134 +0,0 @@ -# -*- coding: utf-8 -*- -# -# This file is part of GetTor, a Tor Browser distribution system. -# -# :authors: Israel Leiva -# -# :copyright: (c) 2015, The Tor Project, Inc. -# (c) 2015, Israel Leiva -# -# :license: This is Free Software. See LICENSE for license information. -# - -import os - -import urllib2 -import json -import argparse -import ConfigParser -import shutil - -# this path should be relative to this script (or absolute) -UPLOAD_SCRIPTS = { - 'dropbox': 'bundles2dropbox.py', - 'drive': 'bundles2drive.py' -} - -# "regex" for filtering downloads in wget -OS_RE = { - 'windows': '%s.exe,%s.exe.asc', - 'linux': '%s.tar.xz,%s.tar.xz.asc', - 'osx': '%s.dmg,%s.dmg.asc', -} - - -def main(): - """Script to fetch the latest Tor Browser. - - Fetch the latest version of Tor Browser and upload it to the supported - providers (e.g. Dropbox). Ideally, this script should be executed with - a cron in order to automate the updating of the files served by GetTor - when a new version of Tor Browser is released. - - Usage: python2.7 fetch.py --os= --lc= - - Some fetch examples: - - Fetch Tor Browser for all platforms and languages: - $ python2.7 fetch.py - - Fetch Tor Browser only for Linux: - $ python2.7 fetch.py --os=linux - - Fetch Tor Browser only for Windows and in US English: - $ python2.7 fetch.py --os=windows --lc=en-US - - Fetch Tor Browser for all platforms, but only in Spanish: - $ python2.7 fetch.py --lc=es-ES - - """ - parser = argparse.ArgumentParser( - description='Utility to fetch the latest Tor Browser and upload it \ - to popular cloud services.' - ) - - # if no OS specified, download all - parser.add_argument('-o', '--os', default=None, - help='filter by OS') - - # if no LC specified, download all - parser.add_argument('-l', '--lc', default='', - help='filter by locale') - - args = parser.parse_args() - - # server from which to download Tor Browser - dist_tpo = 'https://dist.torproject.org/torbrowser/' - - # find out the latest version - url = 'https://www.torproject.org/projects/torbrowser/RecommendedTBBVersions' - response = urllib2.urlopen(url) - json_response = json.load(response) - latest_version = json_response[0] - - # find out the current version delivered by GetTor - config = ConfigParser.RawConfigParser() - config.read('latest_torbrowser.cfg') - current_version = config.get('version', 'current') - - if current_version != latest_version: - mirror = '%s%s/' % (dist_tpo, latest_version) - - # what LC should we download? - lc_re = args.lc - - # what OS should we download? - if args.os == 'windows': - os_re = OS_RE['windows'] % (lc_re, lc_re) - - elif args.os == 'osx': - os_re = OS_RE['osx'] % (lc_re, lc_re) - - elif args.os == 'linux': - os_re = OS_RE['linux'] % (lc_re, lc_re) - - else: - os_re = '%s.exe,%s.exe.asc,%s.dmg,%s.dmg.asc,%s.tar.xz,%s.tar'\ - '.xz.asc' % (lc_re, lc_re, lc_re, lc_re, lc_re, lc_re) - - params = "-nH --cut-dirs=1 -L 1 --accept %s" % os_re - - # in wget we trust - cmd = 'wget %s --mirror %s' % (params, mirror) - - print "Going to execute %s" % cmd - # make the mirror - # a folder with the value of 'latest_version' will be created - os.system(cmd) - # everything inside upload will be uploaded by the provivers' scripts - shutil.move('latest', 'latest_backup') - shutil.move(latest_version, 'latest') - shutil.rmtree('latest_backup') - - # latest version of Tor Browser has been syncronized - # let's upload it - for provider in UPLOAD_SCRIPTS: - os.system('python2.7 %s' % UPLOAD_SCRIPTS[provider]) - - # if everything is OK, update the current version delivered by GetTor - config.set('version', 'current', latest_version) - with open(r'latest_torbrowser.cfg', 'wb') as config_file: - config.write(config_file) - -if __name__ == "__main__": - main() diff --git a/upload/github.cfg b/upload/github.cfg deleted file mode 100644 index 7bdbd90a9dcc602165c714153340b2435c0bffaa..0000000000000000000000000000000000000000 --- a/upload/github.cfg +++ /dev/null @@ -1,8 +0,0 @@ -[general] -upload_dir: latest -tbb_key: torbrowser-key.asc - -[app] -access_token: suchtoken -user: username -repo: gettor-front diff --git a/upload/landing_gh.tpl b/upload/landing_gh.tpl deleted file mode 100644 index 771756abd57742f9da3dc6bf68cda2ce03f41928..0000000000000000000000000000000000000000 --- a/upload/landing_gh.tpl +++ /dev/null @@ -1,137 +0,0 @@ - - - - - - - - - GetTor | Download Tor Browser for Windows, Linux, OS X - - - - - - - - -
-
- -
-
-
- -
-
-

-

Download Tor Browser

-
- Below you will find links to download the latest version of Tor Browser (%TB_VERSION%). -

-
-
-
-
-
-

Direct downloads

- -
-
- -
-
- Tor Browser for Windows
- English, Farsi, Chinese, Turkish -
-
-
-
- -
-
- Tor Browser for OS X
- English, Farsi, Chinese, Turkish -
-
-
-
- -
-
- Tor Browser for Linux 32-bit
- English, Farsi, Chinese, Turkish -
-
-
-
- -
-
- Tor Browser for Linux 64-bit
- English, Farsi, Chinese, Turkish -
-
-
-
-

Alternative downloads

-
- Get links via Email: You can send an email to gettor@torproject.org. - Send the word help in the body of the message to learn how to interact with it. -
-
- Get links via XMPP: You can send a message to get_tor@riseup.net using your favorite XMPP client. Simply - enter help in an XMPP message to learn how to interact with it. -
-
- Get links via Twitter: You can send a direct message to @get_tor account - (you don't need to follow). Send the word help in a direct message to learn - how to interact with it. -
-

Get bridges

-
- Bridges are Tor relays that help you circumvent censorship. If you suspect your access to the - Tor network is being blocked, you may want to use bridges. You can get bridges from - the HTTP distributor. You can also send - an email to bridges@torproject.org - (please note that you must send the email using an address from one of the following email providers: riseup, gmail or yahoo). -
-
-
-
-
- -
- -
-

© The Tor Project 2016

-
- - - - - diff --git a/upload/latest_torbrowser.cfg b/upload/latest_torbrowser.cfg deleted file mode 100644 index 0abe3fb41f92b7511ebcd383867e86d742829d60..0000000000000000000000000000000000000000 --- a/upload/latest_torbrowser.cfg +++ /dev/null @@ -1,3 +0,0 @@ -[version] -current = 4.0.3 - diff --git a/upload/readme_gh.tpl b/upload/readme_gh.tpl deleted file mode 100644 index 63ed23aa631af74a19b9204f6f42488fab4a5ee0..0000000000000000000000000000000000000000 --- a/upload/readme_gh.tpl +++ /dev/null @@ -1,40 +0,0 @@ -# Download Tor Browser - -In this repository you will find links to download the latest version of -Tor Browser, which currently is %TB_VERSION%. Please select one of the links below: - -## Windows -[Download Tor Browser](%WINDOWS_EN%) (English) ([signature file](%WINDOWS_EN_SIG%)). - -[Download Tor Browser](%WINDOWS_FA%) (Farsi) ([signature file](%WINDOWS_FA_SIG%)). - -[Download Tor Browser](%WINDOWS_TR%) (Turkish) ([signature file](%WINDOWS_TR_SIG%)). - -[Download Tor Browser](%WINDOWS_ZH%) (Chinese) ([signature file](%WINDOWS_ZH_SIG%)). - -## OS X -[Download Tor Browser](%OSX_EN%) (English) ([signature file](%OSX_EN_SIG%)). - -[Download Tor Browser](%OSX_FA%) (Farsi) ([signature file](%OSX_FA_SIG%)). - -[Download Tor Browser](%OSX_TR%) (Turkish) ([signature file](%OSX_TR_SIG%)). - -[Download Tor Browser](%OSX_ZH%) (Chinese) ([signature file](%OSX_ZH_SIG%)). - -## Linux 32-bit -[Download Tor Browser](%LINUX32_EN%) (English) ([signature file](%LINUX32_EN_SIG%)). - -[Download Tor Browser](%LINUX32_FA%) (Farsi) ([signature file](%LINUX32_FA_SIG%)). - -[Download Tor Browser](%LINUX32_TR%) (Turkish) ([signature file](%LINUX32_TR_SIG%)). - -[Download Tor Browser](%LINUX32_ZH%) (Chinese) ([signature file](%LINUX32_ZH_SIG%)). - -## Linux 64-bit -[Download Tor Browser](%LINUX64_EN%) (English) ([signature file](%LINUX64_EN_SIG%)). - -[Download Tor Browser](%LINUX64_FA%) (Farsi) ([signature file](%LINUX64_FA_SIG%)). - -[Download Tor Browser](%LINUX64_TR%) (Turkish) ([signature file](%LINUX64_TR_SIG%)). - -[Download Tor Browser](%LINUX64_ZH%) (Chinese) ([signature file](%LINUX64_ZH_SIG%)). diff --git a/upload/torbrowser-key.asc b/upload/torbrowser-key.asc deleted file mode 100644 index 345f65dc140458b1eb89ab346a20480c95191533..0000000000000000000000000000000000000000 Binary files a/upload/torbrowser-key.asc and /dev/null differ diff --git a/www/README.md b/www/README.md deleted file mode 100644 index e28d21679b1794d0624eef68d7783facf8bbe1b7..0000000000000000000000000000000000000000 --- a/www/README.md +++ /dev/null @@ -1,3 +0,0 @@ -This folder contains the webpage rendered at https://gettor.torproject.org. -This is a simple html file at the moment but should be a lektor project and moved -somewhere else. diff --git a/www/css/bootstrap.min.css b/www/css/bootstrap.min.css deleted file mode 100644 index f898a1ac472e1305321def2fc8541c5f88a1c730..0000000000000000000000000000000000000000 --- a/www/css/bootstrap.min.css +++ /dev/null @@ -1,10 +0,0 @@ -/*! - * Bootstrap v3.3.2 (http://getbootstrap.com) - * Copyright 2011-2015 Twitter, Inc. - * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE) - */ - -/*! - * Generated using the Bootstrap Customizer (http://getbootstrap.com/customize/?id=fc8b2e3786f481875a12) - * Config saved to config.json and https://gist.github.com/fc8b2e3786f481875a12 - *//*! normalize.css v3.0.2 | MIT License | git.io/normalize */html{font-family:sans-serif;-ms-text-size-adjust:100%;-webkit-text-size-adjust:100%}body{margin:0}article,aside,details,figcaption,figure,footer,header,hgroup,main,menu,nav,section,summary{display:block}audio,canvas,progress,video{display:inline-block;vertical-align:baseline}audio:not([controls]){display:none;height:0}[hidden],template{display:none}a{background-color:transparent}a:active,a:hover{outline:0}abbr[title]{border-bottom:1px dotted}b,strong{font-weight:bold}dfn{font-style:italic}h1{font-size:2em;margin:0.67em 0}mark{background:#ff0;color:#000}small{font-size:80%}sub,sup{font-size:75%;line-height:0;position:relative;vertical-align:baseline}sup{top:-0.5em}sub{bottom:-0.25em}img{border:0}svg:not(:root){overflow:hidden}figure{margin:1em 40px}hr{-moz-box-sizing:content-box;-webkit-box-sizing:content-box;box-sizing:content-box;height:0}pre{overflow:auto}code,kbd,pre,samp{font-family:monospace, monospace;font-size:1em}button,input,optgroup,select,textarea{color:inherit;font:inherit;margin:0}button{overflow:visible}button,select{text-transform:none}button,html input[type="button"],input[type="reset"],input[type="submit"]{-webkit-appearance:button;cursor:pointer}button[disabled],html input[disabled]{cursor:default}button::-moz-focus-inner,input::-moz-focus-inner{border:0;padding:0}input{line-height:normal}input[type="checkbox"],input[type="radio"]{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box;padding:0}input[type="number"]::-webkit-inner-spin-button,input[type="number"]::-webkit-outer-spin-button{height:auto}input[type="search"]{-webkit-appearance:textfield;-moz-box-sizing:content-box;-webkit-box-sizing:content-box;box-sizing:content-box}input[type="search"]::-webkit-search-cancel-button,input[type="search"]::-webkit-search-decoration{-webkit-appearance:none}fieldset{border:1px solid #c0c0c0;margin:0 2px;padding:0.35em 0.625em 0.75em}legend{border:0;padding:0}textarea{overflow:auto}optgroup{font-weight:bold}table{border-collapse:collapse;border-spacing:0}td,th{padding:0}/*! Source: https://github.com/h5bp/html5-boilerplate/blob/master/src/css/main.css */@media print{*,*:before,*:after{background:transparent !important;color:#000 !important;-webkit-box-shadow:none !important;box-shadow:none !important;text-shadow:none !important}a,a:visited{text-decoration:underline}a[href]:after{content:" (" attr(href) ")"}abbr[title]:after{content:" (" attr(title) ")"}a[href^="#"]:after,a[href^="javascript:"]:after{content:""}pre,blockquote{border:1px solid #999;page-break-inside:avoid}thead{display:table-header-group}tr,img{page-break-inside:avoid}img{max-width:100% !important}p,h2,h3{orphans:3;widows:3}h2,h3{page-break-after:avoid}select{background:#fff !important}.navbar{display:none}.btn>.caret,.dropup>.btn>.caret{border-top-color:#000 !important}.label{border:1px solid #000}.table{border-collapse:collapse !important}.table td,.table th{background-color:#fff !important}.table-bordered th,.table-bordered td{border:1px solid #ddd !important}}@font-face{font-family:'Glyphicons Halflings';src:url('../fonts/glyphicons-halflings-regular.eot');src:url('../fonts/glyphicons-halflings-regular.eot?#iefix') format('embedded-opentype'),url('../fonts/glyphicons-halflings-regular.woff2') format('woff2'),url('../fonts/glyphicons-halflings-regular.woff') format('woff'),url('../fonts/glyphicons-halflings-regular.ttf') format('truetype'),url('../fonts/glyphicons-halflings-regular.svg#glyphicons_halflingsregular') format('svg')}.glyphicon{position:relative;top:1px;display:inline-block;font-family:'Glyphicons Halflings';font-style:normal;font-weight:normal;line-height:1;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.glyphicon-asterisk:before{content:"\2a"}.glyphicon-plus:before{content:"\2b"}.glyphicon-euro:before,.glyphicon-eur:before{content:"\20ac"}.glyphicon-minus:before{content:"\2212"}.glyphicon-cloud:before{content:"\2601"}.glyphicon-envelope:before{content:"\2709"}.glyphicon-pencil:before{content:"\270f"}.glyphicon-glass:before{content:"\e001"}.glyphicon-music:before{content:"\e002"}.glyphicon-search:before{content:"\e003"}.glyphicon-heart:before{content:"\e005"}.glyphicon-star:before{content:"\e006"}.glyphicon-star-empty:before{content:"\e007"}.glyphicon-user:before{content:"\e008"}.glyphicon-film:before{content:"\e009"}.glyphicon-th-large:before{content:"\e010"}.glyphicon-th:before{content:"\e011"}.glyphicon-th-list:before{content:"\e012"}.glyphicon-ok:before{content:"\e013"}.glyphicon-remove:before{content:"\e014"}.glyphicon-zoom-in:before{content:"\e015"}.glyphicon-zoom-out:before{content:"\e016"}.glyphicon-off:before{content:"\e017"}.glyphicon-signal:before{content:"\e018"}.glyphicon-cog:before{content:"\e019"}.glyphicon-trash:before{content:"\e020"}.glyphicon-home:before{content:"\e021"}.glyphicon-file:before{content:"\e022"}.glyphicon-time:before{content:"\e023"}.glyphicon-road:before{content:"\e024"}.glyphicon-download-alt:before{content:"\e025"}.glyphicon-download:before{content:"\e026"}.glyphicon-upload:before{content:"\e027"}.glyphicon-inbox:before{content:"\e028"}.glyphicon-play-circle:before{content:"\e029"}.glyphicon-repeat:before{content:"\e030"}.glyphicon-refresh:before{content:"\e031"}.glyphicon-list-alt:before{content:"\e032"}.glyphicon-lock:before{content:"\e033"}.glyphicon-flag:before{content:"\e034"}.glyphicon-headphones:before{content:"\e035"}.glyphicon-volume-off:before{content:"\e036"}.glyphicon-volume-down:before{content:"\e037"}.glyphicon-volume-up:before{content:"\e038"}.glyphicon-qrcode:before{content:"\e039"}.glyphicon-barcode:before{content:"\e040"}.glyphicon-tag:before{content:"\e041"}.glyphicon-tags:before{content:"\e042"}.glyphicon-book:before{content:"\e043"}.glyphicon-bookmark:before{content:"\e044"}.glyphicon-print:before{content:"\e045"}.glyphicon-camera:before{content:"\e046"}.glyphicon-font:before{content:"\e047"}.glyphicon-bold:before{content:"\e048"}.glyphicon-italic:before{content:"\e049"}.glyphicon-text-height:before{content:"\e050"}.glyphicon-text-width:before{content:"\e051"}.glyphicon-align-left:before{content:"\e052"}.glyphicon-align-center:before{content:"\e053"}.glyphicon-align-right:before{content:"\e054"}.glyphicon-align-justify:before{content:"\e055"}.glyphicon-list:before{content:"\e056"}.glyphicon-indent-left:before{content:"\e057"}.glyphicon-indent-right:before{content:"\e058"}.glyphicon-facetime-video:before{content:"\e059"}.glyphicon-picture:before{content:"\e060"}.glyphicon-map-marker:before{content:"\e062"}.glyphicon-adjust:before{content:"\e063"}.glyphicon-tint:before{content:"\e064"}.glyphicon-edit:before{content:"\e065"}.glyphicon-share:before{content:"\e066"}.glyphicon-check:before{content:"\e067"}.glyphicon-move:before{content:"\e068"}.glyphicon-step-backward:before{content:"\e069"}.glyphicon-fast-backward:before{content:"\e070"}.glyphicon-backward:before{content:"\e071"}.glyphicon-play:before{content:"\e072"}.glyphicon-pause:before{content:"\e073"}.glyphicon-stop:before{content:"\e074"}.glyphicon-forward:before{content:"\e075"}.glyphicon-fast-forward:before{content:"\e076"}.glyphicon-step-forward:before{content:"\e077"}.glyphicon-eject:before{content:"\e078"}.glyphicon-chevron-left:before{content:"\e079"}.glyphicon-chevron-right:before{content:"\e080"}.glyphicon-plus-sign:before{content:"\e081"}.glyphicon-minus-sign:before{content:"\e082"}.glyphicon-remove-sign:before{content:"\e083"}.glyphicon-ok-sign:before{content:"\e084"}.glyphicon-question-sign:before{content:"\e085"}.glyphicon-info-sign:before{content:"\e086"}.glyphicon-screenshot:before{content:"\e087"}.glyphicon-remove-circle:before{content:"\e088"}.glyphicon-ok-circle:before{content:"\e089"}.glyphicon-ban-circle:before{content:"\e090"}.glyphicon-arrow-left:before{content:"\e091"}.glyphicon-arrow-right:before{content:"\e092"}.glyphicon-arrow-up:before{content:"\e093"}.glyphicon-arrow-down:before{content:"\e094"}.glyphicon-share-alt:before{content:"\e095"}.glyphicon-resize-full:before{content:"\e096"}.glyphicon-resize-small:before{content:"\e097"}.glyphicon-exclamation-sign:before{content:"\e101"}.glyphicon-gift:before{content:"\e102"}.glyphicon-leaf:before{content:"\e103"}.glyphicon-fire:before{content:"\e104"}.glyphicon-eye-open:before{content:"\e105"}.glyphicon-eye-close:before{content:"\e106"}.glyphicon-warning-sign:before{content:"\e107"}.glyphicon-plane:before{content:"\e108"}.glyphicon-calendar:before{content:"\e109"}.glyphicon-random:before{content:"\e110"}.glyphicon-comment:before{content:"\e111"}.glyphicon-magnet:before{content:"\e112"}.glyphicon-chevron-up:before{content:"\e113"}.glyphicon-chevron-down:before{content:"\e114"}.glyphicon-retweet:before{content:"\e115"}.glyphicon-shopping-cart:before{content:"\e116"}.glyphicon-folder-close:before{content:"\e117"}.glyphicon-folder-open:before{content:"\e118"}.glyphicon-resize-vertical:before{content:"\e119"}.glyphicon-resize-horizontal:before{content:"\e120"}.glyphicon-hdd:before{content:"\e121"}.glyphicon-bullhorn:before{content:"\e122"}.glyphicon-bell:before{content:"\e123"}.glyphicon-certificate:before{content:"\e124"}.glyphicon-thumbs-up:before{content:"\e125"}.glyphicon-thumbs-down:before{content:"\e126"}.glyphicon-hand-right:before{content:"\e127"}.glyphicon-hand-left:before{content:"\e128"}.glyphicon-hand-up:before{content:"\e129"}.glyphicon-hand-down:before{content:"\e130"}.glyphicon-circle-arrow-right:before{content:"\e131"}.glyphicon-circle-arrow-left:before{content:"\e132"}.glyphicon-circle-arrow-up:before{content:"\e133"}.glyphicon-circle-arrow-down:before{content:"\e134"}.glyphicon-globe:before{content:"\e135"}.glyphicon-wrench:before{content:"\e136"}.glyphicon-tasks:before{content:"\e137"}.glyphicon-filter:before{content:"\e138"}.glyphicon-briefcase:before{content:"\e139"}.glyphicon-fullscreen:before{content:"\e140"}.glyphicon-dashboard:before{content:"\e141"}.glyphicon-paperclip:before{content:"\e142"}.glyphicon-heart-empty:before{content:"\e143"}.glyphicon-link:before{content:"\e144"}.glyphicon-phone:before{content:"\e145"}.glyphicon-pushpin:before{content:"\e146"}.glyphicon-usd:before{content:"\e148"}.glyphicon-gbp:before{content:"\e149"}.glyphicon-sort:before{content:"\e150"}.glyphicon-sort-by-alphabet:before{content:"\e151"}.glyphicon-sort-by-alphabet-alt:before{content:"\e152"}.glyphicon-sort-by-order:before{content:"\e153"}.glyphicon-sort-by-order-alt:before{content:"\e154"}.glyphicon-sort-by-attributes:before{content:"\e155"}.glyphicon-sort-by-attributes-alt:before{content:"\e156"}.glyphicon-unchecked:before{content:"\e157"}.glyphicon-expand:before{content:"\e158"}.glyphicon-collapse-down:before{content:"\e159"}.glyphicon-collapse-up:before{content:"\e160"}.glyphicon-log-in:before{content:"\e161"}.glyphicon-flash:before{content:"\e162"}.glyphicon-log-out:before{content:"\e163"}.glyphicon-new-window:before{content:"\e164"}.glyphicon-record:before{content:"\e165"}.glyphicon-save:before{content:"\e166"}.glyphicon-open:before{content:"\e167"}.glyphicon-saved:before{content:"\e168"}.glyphicon-import:before{content:"\e169"}.glyphicon-export:before{content:"\e170"}.glyphicon-send:before{content:"\e171"}.glyphicon-floppy-disk:before{content:"\e172"}.glyphicon-floppy-saved:before{content:"\e173"}.glyphicon-floppy-remove:before{content:"\e174"}.glyphicon-floppy-save:before{content:"\e175"}.glyphicon-floppy-open:before{content:"\e176"}.glyphicon-credit-card:before{content:"\e177"}.glyphicon-transfer:before{content:"\e178"}.glyphicon-cutlery:before{content:"\e179"}.glyphicon-header:before{content:"\e180"}.glyphicon-compressed:before{content:"\e181"}.glyphicon-earphone:before{content:"\e182"}.glyphicon-phone-alt:before{content:"\e183"}.glyphicon-tower:before{content:"\e184"}.glyphicon-stats:before{content:"\e185"}.glyphicon-sd-video:before{content:"\e186"}.glyphicon-hd-video:before{content:"\e187"}.glyphicon-subtitles:before{content:"\e188"}.glyphicon-sound-stereo:before{content:"\e189"}.glyphicon-sound-dolby:before{content:"\e190"}.glyphicon-sound-5-1:before{content:"\e191"}.glyphicon-sound-6-1:before{content:"\e192"}.glyphicon-sound-7-1:before{content:"\e193"}.glyphicon-copyright-mark:before{content:"\e194"}.glyphicon-registration-mark:before{content:"\e195"}.glyphicon-cloud-download:before{content:"\e197"}.glyphicon-cloud-upload:before{content:"\e198"}.glyphicon-tree-conifer:before{content:"\e199"}.glyphicon-tree-deciduous:before{content:"\e200"}.glyphicon-cd:before{content:"\e201"}.glyphicon-save-file:before{content:"\e202"}.glyphicon-open-file:before{content:"\e203"}.glyphicon-level-up:before{content:"\e204"}.glyphicon-copy:before{content:"\e205"}.glyphicon-paste:before{content:"\e206"}.glyphicon-alert:before{content:"\e209"}.glyphicon-equalizer:before{content:"\e210"}.glyphicon-king:before{content:"\e211"}.glyphicon-queen:before{content:"\e212"}.glyphicon-pawn:before{content:"\e213"}.glyphicon-bishop:before{content:"\e214"}.glyphicon-knight:before{content:"\e215"}.glyphicon-baby-formula:before{content:"\e216"}.glyphicon-tent:before{content:"\26fa"}.glyphicon-blackboard:before{content:"\e218"}.glyphicon-bed:before{content:"\e219"}.glyphicon-apple:before{content:"\f8ff"}.glyphicon-erase:before{content:"\e221"}.glyphicon-hourglass:before{content:"\231b"}.glyphicon-lamp:before{content:"\e223"}.glyphicon-duplicate:before{content:"\e224"}.glyphicon-piggy-bank:before{content:"\e225"}.glyphicon-scissors:before{content:"\e226"}.glyphicon-bitcoin:before{content:"\e227"}.glyphicon-yen:before{content:"\00a5"}.glyphicon-ruble:before{content:"\20bd"}.glyphicon-scale:before{content:"\e230"}.glyphicon-ice-lolly:before{content:"\e231"}.glyphicon-ice-lolly-tasted:before{content:"\e232"}.glyphicon-education:before{content:"\e233"}.glyphicon-option-horizontal:before{content:"\e234"}.glyphicon-option-vertical:before{content:"\e235"}.glyphicon-menu-hamburger:before{content:"\e236"}.glyphicon-modal-window:before{content:"\e237"}.glyphicon-oil:before{content:"\e238"}.glyphicon-grain:before{content:"\e239"}.glyphicon-sunglasses:before{content:"\e240"}.glyphicon-text-size:before{content:"\e241"}.glyphicon-text-color:before{content:"\e242"}.glyphicon-text-background:before{content:"\e243"}.glyphicon-object-align-top:before{content:"\e244"}.glyphicon-object-align-bottom:before{content:"\e245"}.glyphicon-object-align-horizontal:before{content:"\e246"}.glyphicon-object-align-left:before{content:"\e247"}.glyphicon-object-align-vertical:before{content:"\e248"}.glyphicon-object-align-right:before{content:"\e249"}.glyphicon-triangle-right:before{content:"\e250"}.glyphicon-triangle-left:before{content:"\e251"}.glyphicon-triangle-bottom:before{content:"\e252"}.glyphicon-triangle-top:before{content:"\e253"}.glyphicon-console:before{content:"\e254"}.glyphicon-superscript:before{content:"\e255"}.glyphicon-subscript:before{content:"\e256"}.glyphicon-menu-left:before{content:"\e257"}.glyphicon-menu-right:before{content:"\e258"}.glyphicon-menu-down:before{content:"\e259"}.glyphicon-menu-up:before{content:"\e260"}*{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}*:before,*:after{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}html{font-size:10px;-webkit-tap-highlight-color:rgba(0,0,0,0)}body{font-family:"Helvetica Neue",Helvetica,Arial,sans-serif;font-size:14px;line-height:1.42857143;color:#333;background-color:#fff}input,button,select,textarea{font-family:inherit;font-size:inherit;line-height:inherit}a{color:#337ab7;text-decoration:none}a:hover,a:focus{color:#23527c;text-decoration:underline}a:focus{outline:thin dotted;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}figure{margin:0}img{vertical-align:middle}.img-responsive{display:block;max-width:100%;height:auto}.img-rounded{border-radius:6px}.img-thumbnail{padding:4px;line-height:1.42857143;background-color:#fff;border:1px solid #ddd;border-radius:4px;-webkit-transition:all .2s ease-in-out;-o-transition:all .2s ease-in-out;transition:all .2s ease-in-out;display:inline-block;max-width:100%;height:auto}.img-circle{border-radius:50%}hr{margin-top:20px;margin-bottom:20px;border:0;border-top:1px solid #eee}.sr-only{position:absolute;width:1px;height:1px;margin:-1px;padding:0;overflow:hidden;clip:rect(0, 0, 0, 0);border:0}.sr-only-focusable:active,.sr-only-focusable:focus{position:static;width:auto;height:auto;margin:0;overflow:visible;clip:auto}h1,h2,h3,h4,h5,h6,.h1,.h2,.h3,.h4,.h5,.h6{font-family:inherit;font-weight:500;line-height:1.1;color:inherit}h1 small,h2 small,h3 small,h4 small,h5 small,h6 small,.h1 small,.h2 small,.h3 small,.h4 small,.h5 small,.h6 small,h1 .small,h2 .small,h3 .small,h4 .small,h5 .small,h6 .small,.h1 .small,.h2 .small,.h3 .small,.h4 .small,.h5 .small,.h6 .small{font-weight:normal;line-height:1;color:#777}h1,.h1,h2,.h2,h3,.h3{margin-top:20px;margin-bottom:10px}h1 small,.h1 small,h2 small,.h2 small,h3 small,.h3 small,h1 .small,.h1 .small,h2 .small,.h2 .small,h3 .small,.h3 .small{font-size:65%}h4,.h4,h5,.h5,h6,.h6{margin-top:10px;margin-bottom:10px}h4 small,.h4 small,h5 small,.h5 small,h6 small,.h6 small,h4 .small,.h4 .small,h5 .small,.h5 .small,h6 .small,.h6 .small{font-size:75%}h1,.h1{font-size:36px}h2,.h2{font-size:30px}h3,.h3{font-size:24px}h4,.h4{font-size:18px}h5,.h5{font-size:14px}h6,.h6{font-size:12px}p{margin:0 0 10px}.lead{margin-bottom:20px;font-size:16px;font-weight:300;line-height:1.4}@media (min-width:768px){.lead{font-size:21px}}small,.small{font-size:85%}mark,.mark{background-color:#fcf8e3;padding:.2em}.text-left{text-align:left}.text-right{text-align:right}.text-center{text-align:center}.text-justify{text-align:justify}.text-nowrap{white-space:nowrap}.text-lowercase{text-transform:lowercase}.text-uppercase{text-transform:uppercase}.text-capitalize{text-transform:capitalize}.text-muted{color:#777}.text-primary{color:#337ab7}a.text-primary:hover{color:#286090}.text-success{color:#3c763d}a.text-success:hover{color:#2b542c}.text-info{color:#31708f}a.text-info:hover{color:#245269}.text-warning{color:#8a6d3b}a.text-warning:hover{color:#66512c}.text-danger{color:#a94442}a.text-danger:hover{color:#843534}.bg-primary{color:#fff;background-color:#337ab7}a.bg-primary:hover{background-color:#286090}.bg-success{background-color:#dff0d8}a.bg-success:hover{background-color:#c1e2b3}.bg-info{background-color:#d9edf7}a.bg-info:hover{background-color:#afd9ee}.bg-warning{background-color:#fcf8e3}a.bg-warning:hover{background-color:#f7ecb5}.bg-danger{background-color:#f2dede}a.bg-danger:hover{background-color:#e4b9b9}.page-header{padding-bottom:9px;margin:40px 0 20px;border-bottom:1px solid #eee}ul,ol{margin-top:0;margin-bottom:10px}ul ul,ol ul,ul ol,ol ol{margin-bottom:0}.list-unstyled{padding-left:0;list-style:none}.list-inline{padding-left:0;list-style:none;margin-left:-5px}.list-inline>li{display:inline-block;padding-left:5px;padding-right:5px}dl{margin-top:0;margin-bottom:20px}dt,dd{line-height:1.42857143}dt{font-weight:bold}dd{margin-left:0}@media (min-width:768px){.dl-horizontal dt{float:left;width:160px;clear:left;text-align:right;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.dl-horizontal dd{margin-left:180px}}abbr[title],abbr[data-original-title]{cursor:help;border-bottom:1px dotted #777}.well{min-height:20px;padding:19px;margin-bottom:20px;background-color:#f5f5f5;border:1px solid #e3e3e3;border-radius:4px;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.05);box-shadow:inset 0 1px 1px rgba(0,0,0,.05)}.initialism{font-size:90%;text-transform:uppercase}blockquote{padding:10px 20px;margin:0 0 20px;font-size:17.5px;border-left:5px solid #eee}blockquote p:last-child,blockquote ul:last-child,blockquote ol:last-child{margin-bottom:0}blockquote footer,blockquote small,blockquote .small{display:block;font-size:80%;line-height:1.42857143;color:#777}blockquote footer:before,blockquote small:before,blockquote .small:before{content:'\2014 \00A0'}.blockquote-reverse,blockquote.pull-right{padding-right:15px;padding-left:0;border-right:5px solid #eee;border-left:0;text-align:right}.blockquote-reverse footer:before,blockquote.pull-right footer:before,.blockquote-reverse small:before,blockquote.pull-right small:before,.blockquote-reverse .small:before,blockquote.pull-right .small:before{content:''}.blockquote-reverse footer:after,blockquote.pull-right footer:after,.blockquote-reverse small:after,blockquote.pull-right small:after,.blockquote-reverse .small:after,blockquote.pull-right .small:after{content:'\00A0 \2014'}address{margin-bottom:20px;font-style:normal;line-height:1.42857143}code,kbd,pre,samp{font-family:Menlo,Monaco,Consolas,"Courier New",monospace}code{padding:2px 4px;font-size:90%;color:#c7254e;background-color:#f9f2f4;border-radius:4px}kbd{padding:2px 4px;font-size:90%;color:#fff;background-color:#333;border-radius:3px;-webkit-box-shadow:inset 0 -1px 0 rgba(0,0,0,0.25);box-shadow:inset 0 -1px 0 rgba(0,0,0,0.25)}kbd kbd{padding:0;font-size:100%;font-weight:bold;-webkit-box-shadow:none;box-shadow:none}pre{display:block;padding:9.5px;margin:0 0 10px;font-size:13px;line-height:1.42857143;word-break:break-all;word-wrap:break-word;color:#333;background-color:#f5f5f5;border:1px solid #ccc;border-radius:4px}pre code{padding:0;font-size:inherit;color:inherit;white-space:pre-wrap;background-color:transparent;border-radius:0}.pre-scrollable{max-height:340px;overflow-y:scroll}.container{margin-right:auto;margin-left:auto;padding-left:15px;padding-right:15px}@media (min-width:768px){.container{width:750px}}@media (min-width:992px){.container{width:970px}}@media (min-width:1200px){.container{width:1170px}}.container-fluid{margin-right:auto;margin-left:auto;padding-left:15px;padding-right:15px}.row{margin-left:-15px;margin-right:-15px}.col-xs-1, .col-sm-1, .col-md-1, .col-lg-1, .col-xs-2, .col-sm-2, .col-md-2, .col-lg-2, .col-xs-3, .col-sm-3, .col-md-3, .col-lg-3, .col-xs-4, .col-sm-4, .col-md-4, .col-lg-4, .col-xs-5, .col-sm-5, .col-md-5, .col-lg-5, .col-xs-6, .col-sm-6, .col-md-6, .col-lg-6, .col-xs-7, .col-sm-7, .col-md-7, .col-lg-7, .col-xs-8, .col-sm-8, .col-md-8, .col-lg-8, .col-xs-9, .col-sm-9, .col-md-9, .col-lg-9, .col-xs-10, .col-sm-10, .col-md-10, .col-lg-10, .col-xs-11, .col-sm-11, .col-md-11, .col-lg-11, .col-xs-12, .col-sm-12, .col-md-12, .col-lg-12{position:relative;min-height:1px;padding-left:15px;padding-right:15px}.col-xs-1, .col-xs-2, .col-xs-3, .col-xs-4, .col-xs-5, .col-xs-6, .col-xs-7, .col-xs-8, .col-xs-9, .col-xs-10, .col-xs-11, .col-xs-12{float:left}.col-xs-12{width:100%}.col-xs-11{width:91.66666667%}.col-xs-10{width:83.33333333%}.col-xs-9{width:75%}.col-xs-8{width:66.66666667%}.col-xs-7{width:58.33333333%}.col-xs-6{width:50%}.col-xs-5{width:41.66666667%}.col-xs-4{width:33.33333333%}.col-xs-3{width:25%}.col-xs-2{width:16.66666667%}.col-xs-1{width:8.33333333%}.col-xs-pull-12{right:100%}.col-xs-pull-11{right:91.66666667%}.col-xs-pull-10{right:83.33333333%}.col-xs-pull-9{right:75%}.col-xs-pull-8{right:66.66666667%}.col-xs-pull-7{right:58.33333333%}.col-xs-pull-6{right:50%}.col-xs-pull-5{right:41.66666667%}.col-xs-pull-4{right:33.33333333%}.col-xs-pull-3{right:25%}.col-xs-pull-2{right:16.66666667%}.col-xs-pull-1{right:8.33333333%}.col-xs-pull-0{right:auto}.col-xs-push-12{left:100%}.col-xs-push-11{left:91.66666667%}.col-xs-push-10{left:83.33333333%}.col-xs-push-9{left:75%}.col-xs-push-8{left:66.66666667%}.col-xs-push-7{left:58.33333333%}.col-xs-push-6{left:50%}.col-xs-push-5{left:41.66666667%}.col-xs-push-4{left:33.33333333%}.col-xs-push-3{left:25%}.col-xs-push-2{left:16.66666667%}.col-xs-push-1{left:8.33333333%}.col-xs-push-0{left:auto}.col-xs-offset-12{margin-left:100%}.col-xs-offset-11{margin-left:91.66666667%}.col-xs-offset-10{margin-left:83.33333333%}.col-xs-offset-9{margin-left:75%}.col-xs-offset-8{margin-left:66.66666667%}.col-xs-offset-7{margin-left:58.33333333%}.col-xs-offset-6{margin-left:50%}.col-xs-offset-5{margin-left:41.66666667%}.col-xs-offset-4{margin-left:33.33333333%}.col-xs-offset-3{margin-left:25%}.col-xs-offset-2{margin-left:16.66666667%}.col-xs-offset-1{margin-left:8.33333333%}.col-xs-offset-0{margin-left:0}@media (min-width:768px){.col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12{float:left}.col-sm-12{width:100%}.col-sm-11{width:91.66666667%}.col-sm-10{width:83.33333333%}.col-sm-9{width:75%}.col-sm-8{width:66.66666667%}.col-sm-7{width:58.33333333%}.col-sm-6{width:50%}.col-sm-5{width:41.66666667%}.col-sm-4{width:33.33333333%}.col-sm-3{width:25%}.col-sm-2{width:16.66666667%}.col-sm-1{width:8.33333333%}.col-sm-pull-12{right:100%}.col-sm-pull-11{right:91.66666667%}.col-sm-pull-10{right:83.33333333%}.col-sm-pull-9{right:75%}.col-sm-pull-8{right:66.66666667%}.col-sm-pull-7{right:58.33333333%}.col-sm-pull-6{right:50%}.col-sm-pull-5{right:41.66666667%}.col-sm-pull-4{right:33.33333333%}.col-sm-pull-3{right:25%}.col-sm-pull-2{right:16.66666667%}.col-sm-pull-1{right:8.33333333%}.col-sm-pull-0{right:auto}.col-sm-push-12{left:100%}.col-sm-push-11{left:91.66666667%}.col-sm-push-10{left:83.33333333%}.col-sm-push-9{left:75%}.col-sm-push-8{left:66.66666667%}.col-sm-push-7{left:58.33333333%}.col-sm-push-6{left:50%}.col-sm-push-5{left:41.66666667%}.col-sm-push-4{left:33.33333333%}.col-sm-push-3{left:25%}.col-sm-push-2{left:16.66666667%}.col-sm-push-1{left:8.33333333%}.col-sm-push-0{left:auto}.col-sm-offset-12{margin-left:100%}.col-sm-offset-11{margin-left:91.66666667%}.col-sm-offset-10{margin-left:83.33333333%}.col-sm-offset-9{margin-left:75%}.col-sm-offset-8{margin-left:66.66666667%}.col-sm-offset-7{margin-left:58.33333333%}.col-sm-offset-6{margin-left:50%}.col-sm-offset-5{margin-left:41.66666667%}.col-sm-offset-4{margin-left:33.33333333%}.col-sm-offset-3{margin-left:25%}.col-sm-offset-2{margin-left:16.66666667%}.col-sm-offset-1{margin-left:8.33333333%}.col-sm-offset-0{margin-left:0}}@media (min-width:992px){.col-md-1, .col-md-2, .col-md-3, .col-md-4, .col-md-5, .col-md-6, .col-md-7, .col-md-8, .col-md-9, .col-md-10, .col-md-11, .col-md-12{float:left}.col-md-12{width:100%}.col-md-11{width:91.66666667%}.col-md-10{width:83.33333333%}.col-md-9{width:75%}.col-md-8{width:66.66666667%}.col-md-7{width:58.33333333%}.col-md-6{width:50%}.col-md-5{width:41.66666667%}.col-md-4{width:33.33333333%}.col-md-3{width:25%}.col-md-2{width:16.66666667%}.col-md-1{width:8.33333333%}.col-md-pull-12{right:100%}.col-md-pull-11{right:91.66666667%}.col-md-pull-10{right:83.33333333%}.col-md-pull-9{right:75%}.col-md-pull-8{right:66.66666667%}.col-md-pull-7{right:58.33333333%}.col-md-pull-6{right:50%}.col-md-pull-5{right:41.66666667%}.col-md-pull-4{right:33.33333333%}.col-md-pull-3{right:25%}.col-md-pull-2{right:16.66666667%}.col-md-pull-1{right:8.33333333%}.col-md-pull-0{right:auto}.col-md-push-12{left:100%}.col-md-push-11{left:91.66666667%}.col-md-push-10{left:83.33333333%}.col-md-push-9{left:75%}.col-md-push-8{left:66.66666667%}.col-md-push-7{left:58.33333333%}.col-md-push-6{left:50%}.col-md-push-5{left:41.66666667%}.col-md-push-4{left:33.33333333%}.col-md-push-3{left:25%}.col-md-push-2{left:16.66666667%}.col-md-push-1{left:8.33333333%}.col-md-push-0{left:auto}.col-md-offset-12{margin-left:100%}.col-md-offset-11{margin-left:91.66666667%}.col-md-offset-10{margin-left:83.33333333%}.col-md-offset-9{margin-left:75%}.col-md-offset-8{margin-left:66.66666667%}.col-md-offset-7{margin-left:58.33333333%}.col-md-offset-6{margin-left:50%}.col-md-offset-5{margin-left:41.66666667%}.col-md-offset-4{margin-left:33.33333333%}.col-md-offset-3{margin-left:25%}.col-md-offset-2{margin-left:16.66666667%}.col-md-offset-1{margin-left:8.33333333%}.col-md-offset-0{margin-left:0}}@media (min-width:1200px){.col-lg-1, .col-lg-2, .col-lg-3, .col-lg-4, .col-lg-5, .col-lg-6, .col-lg-7, .col-lg-8, .col-lg-9, .col-lg-10, .col-lg-11, .col-lg-12{float:left}.col-lg-12{width:100%}.col-lg-11{width:91.66666667%}.col-lg-10{width:83.33333333%}.col-lg-9{width:75%}.col-lg-8{width:66.66666667%}.col-lg-7{width:58.33333333%}.col-lg-6{width:50%}.col-lg-5{width:41.66666667%}.col-lg-4{width:33.33333333%}.col-lg-3{width:25%}.col-lg-2{width:16.66666667%}.col-lg-1{width:8.33333333%}.col-lg-pull-12{right:100%}.col-lg-pull-11{right:91.66666667%}.col-lg-pull-10{right:83.33333333%}.col-lg-pull-9{right:75%}.col-lg-pull-8{right:66.66666667%}.col-lg-pull-7{right:58.33333333%}.col-lg-pull-6{right:50%}.col-lg-pull-5{right:41.66666667%}.col-lg-pull-4{right:33.33333333%}.col-lg-pull-3{right:25%}.col-lg-pull-2{right:16.66666667%}.col-lg-pull-1{right:8.33333333%}.col-lg-pull-0{right:auto}.col-lg-push-12{left:100%}.col-lg-push-11{left:91.66666667%}.col-lg-push-10{left:83.33333333%}.col-lg-push-9{left:75%}.col-lg-push-8{left:66.66666667%}.col-lg-push-7{left:58.33333333%}.col-lg-push-6{left:50%}.col-lg-push-5{left:41.66666667%}.col-lg-push-4{left:33.33333333%}.col-lg-push-3{left:25%}.col-lg-push-2{left:16.66666667%}.col-lg-push-1{left:8.33333333%}.col-lg-push-0{left:auto}.col-lg-offset-12{margin-left:100%}.col-lg-offset-11{margin-left:91.66666667%}.col-lg-offset-10{margin-left:83.33333333%}.col-lg-offset-9{margin-left:75%}.col-lg-offset-8{margin-left:66.66666667%}.col-lg-offset-7{margin-left:58.33333333%}.col-lg-offset-6{margin-left:50%}.col-lg-offset-5{margin-left:41.66666667%}.col-lg-offset-4{margin-left:33.33333333%}.col-lg-offset-3{margin-left:25%}.col-lg-offset-2{margin-left:16.66666667%}.col-lg-offset-1{margin-left:8.33333333%}.col-lg-offset-0{margin-left:0}}fieldset{padding:0;margin:0;border:0;min-width:0}legend{display:block;width:100%;padding:0;margin-bottom:20px;font-size:21px;line-height:inherit;color:#333;border:0;border-bottom:1px solid #e5e5e5}label{display:inline-block;max-width:100%;margin-bottom:5px;font-weight:bold}input[type="search"]{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}input[type="radio"],input[type="checkbox"]{margin:4px 0 0;margin-top:1px \9;line-height:normal}input[type="file"]{display:block}input[type="range"]{display:block;width:100%}select[multiple],select[size]{height:auto}input[type="file"]:focus,input[type="radio"]:focus,input[type="checkbox"]:focus{outline:thin dotted;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}output{display:block;padding-top:7px;font-size:14px;line-height:1.42857143;color:#555}.form-control{display:block;width:100%;height:34px;padding:6px 12px;font-size:14px;line-height:1.42857143;color:#555;background-color:#fff;background-image:none;border:1px solid #ccc;border-radius:4px;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);-webkit-transition:border-color ease-in-out .15s, -webkit-box-shadow ease-in-out .15s;-o-transition:border-color ease-in-out .15s, box-shadow ease-in-out .15s;transition:border-color ease-in-out .15s, box-shadow ease-in-out .15s}.form-control:focus{border-color:#66afe9;outline:0;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);box-shadow:inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6)}.form-control::-moz-placeholder{color:#999;opacity:1}.form-control:-ms-input-placeholder{color:#999}.form-control::-webkit-input-placeholder{color:#999}.form-control[disabled],.form-control[readonly],fieldset[disabled] .form-control{cursor:not-allowed;background-color:#eee;opacity:1}textarea.form-control{height:auto}input[type="search"]{-webkit-appearance:none}@media screen and (-webkit-min-device-pixel-ratio:0){input[type="date"],input[type="time"],input[type="datetime-local"],input[type="month"]{line-height:34px}input[type="date"].input-sm,input[type="time"].input-sm,input[type="datetime-local"].input-sm,input[type="month"].input-sm,.input-group-sm input[type="date"],.input-group-sm input[type="time"],.input-group-sm input[type="datetime-local"],.input-group-sm input[type="month"]{line-height:30px}input[type="date"].input-lg,input[type="time"].input-lg,input[type="datetime-local"].input-lg,input[type="month"].input-lg,.input-group-lg input[type="date"],.input-group-lg input[type="time"],.input-group-lg input[type="datetime-local"],.input-group-lg input[type="month"]{line-height:46px}}.form-group{margin-bottom:15px}.radio,.checkbox{position:relative;display:block;margin-top:10px;margin-bottom:10px}.radio label,.checkbox label{min-height:20px;padding-left:20px;margin-bottom:0;font-weight:normal;cursor:pointer}.radio input[type="radio"],.radio-inline input[type="radio"],.checkbox input[type="checkbox"],.checkbox-inline input[type="checkbox"]{position:absolute;margin-left:-20px;margin-top:4px \9}.radio+.radio,.checkbox+.checkbox{margin-top:-5px}.radio-inline,.checkbox-inline{display:inline-block;padding-left:20px;margin-bottom:0;vertical-align:middle;font-weight:normal;cursor:pointer}.radio-inline+.radio-inline,.checkbox-inline+.checkbox-inline{margin-top:0;margin-left:10px}input[type="radio"][disabled],input[type="checkbox"][disabled],input[type="radio"].disabled,input[type="checkbox"].disabled,fieldset[disabled] input[type="radio"],fieldset[disabled] input[type="checkbox"]{cursor:not-allowed}.radio-inline.disabled,.checkbox-inline.disabled,fieldset[disabled] .radio-inline,fieldset[disabled] .checkbox-inline{cursor:not-allowed}.radio.disabled label,.checkbox.disabled label,fieldset[disabled] .radio label,fieldset[disabled] .checkbox label{cursor:not-allowed}.form-control-static{padding-top:7px;padding-bottom:7px;margin-bottom:0}.form-control-static.input-lg,.form-control-static.input-sm{padding-left:0;padding-right:0}.input-sm{height:30px;padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}select.input-sm{height:30px;line-height:30px}textarea.input-sm,select[multiple].input-sm{height:auto}.form-group-sm .form-control{height:30px;padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}select.form-group-sm .form-control{height:30px;line-height:30px}textarea.form-group-sm .form-control,select[multiple].form-group-sm .form-control{height:auto}.form-group-sm .form-control-static{height:30px;padding:5px 10px;font-size:12px;line-height:1.5}.input-lg{height:46px;padding:10px 16px;font-size:18px;line-height:1.3333333;border-radius:6px}select.input-lg{height:46px;line-height:46px}textarea.input-lg,select[multiple].input-lg{height:auto}.form-group-lg .form-control{height:46px;padding:10px 16px;font-size:18px;line-height:1.3333333;border-radius:6px}select.form-group-lg .form-control{height:46px;line-height:46px}textarea.form-group-lg .form-control,select[multiple].form-group-lg .form-control{height:auto}.form-group-lg .form-control-static{height:46px;padding:10px 16px;font-size:18px;line-height:1.3333333}.has-feedback{position:relative}.has-feedback .form-control{padding-right:42.5px}.form-control-feedback{position:absolute;top:0;right:0;z-index:2;display:block;width:34px;height:34px;line-height:34px;text-align:center;pointer-events:none}.input-lg+.form-control-feedback{width:46px;height:46px;line-height:46px}.input-sm+.form-control-feedback{width:30px;height:30px;line-height:30px}.has-success .help-block,.has-success .control-label,.has-success .radio,.has-success .checkbox,.has-success .radio-inline,.has-success .checkbox-inline,.has-success.radio label,.has-success.checkbox label,.has-success.radio-inline label,.has-success.checkbox-inline label{color:#3c763d}.has-success .form-control{border-color:#3c763d;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075)}.has-success .form-control:focus{border-color:#2b542c;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #67b168;box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #67b168}.has-success .input-group-addon{color:#3c763d;border-color:#3c763d;background-color:#dff0d8}.has-success .form-control-feedback{color:#3c763d}.has-warning .help-block,.has-warning .control-label,.has-warning .radio,.has-warning .checkbox,.has-warning .radio-inline,.has-warning .checkbox-inline,.has-warning.radio label,.has-warning.checkbox label,.has-warning.radio-inline label,.has-warning.checkbox-inline label{color:#8a6d3b}.has-warning .form-control{border-color:#8a6d3b;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075)}.has-warning .form-control:focus{border-color:#66512c;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #c0a16b;box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #c0a16b}.has-warning .input-group-addon{color:#8a6d3b;border-color:#8a6d3b;background-color:#fcf8e3}.has-warning .form-control-feedback{color:#8a6d3b}.has-error .help-block,.has-error .control-label,.has-error .radio,.has-error .checkbox,.has-error .radio-inline,.has-error .checkbox-inline,.has-error.radio label,.has-error.checkbox label,.has-error.radio-inline label,.has-error.checkbox-inline label{color:#a94442}.has-error .form-control{border-color:#a94442;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075);box-shadow:inset 0 1px 1px rgba(0,0,0,0.075)}.has-error .form-control:focus{border-color:#843534;-webkit-box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #ce8483;box-shadow:inset 0 1px 1px rgba(0,0,0,0.075),0 0 6px #ce8483}.has-error .input-group-addon{color:#a94442;border-color:#a94442;background-color:#f2dede}.has-error .form-control-feedback{color:#a94442}.has-feedback label~.form-control-feedback{top:25px}.has-feedback label.sr-only~.form-control-feedback{top:0}.help-block{display:block;margin-top:5px;margin-bottom:10px;color:#737373}@media (min-width:768px){.form-inline .form-group{display:inline-block;margin-bottom:0;vertical-align:middle}.form-inline .form-control{display:inline-block;width:auto;vertical-align:middle}.form-inline .form-control-static{display:inline-block}.form-inline .input-group{display:inline-table;vertical-align:middle}.form-inline .input-group .input-group-addon,.form-inline .input-group .input-group-btn,.form-inline .input-group .form-control{width:auto}.form-inline .input-group>.form-control{width:100%}.form-inline .control-label{margin-bottom:0;vertical-align:middle}.form-inline .radio,.form-inline .checkbox{display:inline-block;margin-top:0;margin-bottom:0;vertical-align:middle}.form-inline .radio label,.form-inline .checkbox label{padding-left:0}.form-inline .radio input[type="radio"],.form-inline .checkbox input[type="checkbox"]{position:relative;margin-left:0}.form-inline .has-feedback .form-control-feedback{top:0}}.form-horizontal .radio,.form-horizontal .checkbox,.form-horizontal .radio-inline,.form-horizontal .checkbox-inline{margin-top:0;margin-bottom:0;padding-top:7px}.form-horizontal .radio,.form-horizontal .checkbox{min-height:27px}.form-horizontal .form-group{margin-left:-15px;margin-right:-15px}@media (min-width:768px){.form-horizontal .control-label{text-align:right;margin-bottom:0;padding-top:7px}}.form-horizontal .has-feedback .form-control-feedback{right:15px}@media (min-width:768px){.form-horizontal .form-group-lg .control-label{padding-top:14.333333px}}@media (min-width:768px){.form-horizontal .form-group-sm .control-label{padding-top:6px}}.btn{display:inline-block;margin-bottom:0;font-weight:normal;text-align:center;vertical-align:middle;-ms-touch-action:manipulation;touch-action:manipulation;cursor:pointer;background-image:none;border:1px solid transparent;white-space:nowrap;padding:6px 12px;font-size:14px;line-height:1.42857143;border-radius:4px;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}.btn:focus,.btn:active:focus,.btn.active:focus,.btn.focus,.btn:active.focus,.btn.active.focus{outline:thin dotted;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}.btn:hover,.btn:focus,.btn.focus{color:#333;text-decoration:none}.btn:active,.btn.active{outline:0;background-image:none;-webkit-box-shadow:inset 0 3px 5px rgba(0,0,0,0.125);box-shadow:inset 0 3px 5px rgba(0,0,0,0.125)}.btn.disabled,.btn[disabled],fieldset[disabled] .btn{cursor:not-allowed;pointer-events:none;opacity:.65;filter:alpha(opacity=65);-webkit-box-shadow:none;box-shadow:none}.btn-default{color:#333;background-color:#fff;border-color:#ccc}.btn-default:hover,.btn-default:focus,.btn-default.focus,.btn-default:active,.btn-default.active,.open>.dropdown-toggle.btn-default{color:#333;background-color:#e6e6e6;border-color:#adadad}.btn-default:active,.btn-default.active,.open>.dropdown-toggle.btn-default{background-image:none}.btn-default.disabled,.btn-default[disabled],fieldset[disabled] .btn-default,.btn-default.disabled:hover,.btn-default[disabled]:hover,fieldset[disabled] .btn-default:hover,.btn-default.disabled:focus,.btn-default[disabled]:focus,fieldset[disabled] .btn-default:focus,.btn-default.disabled.focus,.btn-default[disabled].focus,fieldset[disabled] .btn-default.focus,.btn-default.disabled:active,.btn-default[disabled]:active,fieldset[disabled] .btn-default:active,.btn-default.disabled.active,.btn-default[disabled].active,fieldset[disabled] .btn-default.active{background-color:#fff;border-color:#ccc}.btn-default .badge{color:#fff;background-color:#333}.btn-primary{color:#fff;background-color:#337ab7;border-color:#2e6da4}.btn-primary:hover,.btn-primary:focus,.btn-primary.focus,.btn-primary:active,.btn-primary.active,.open>.dropdown-toggle.btn-primary{color:#fff;background-color:#286090;border-color:#204d74}.btn-primary:active,.btn-primary.active,.open>.dropdown-toggle.btn-primary{background-image:none}.btn-primary.disabled,.btn-primary[disabled],fieldset[disabled] .btn-primary,.btn-primary.disabled:hover,.btn-primary[disabled]:hover,fieldset[disabled] .btn-primary:hover,.btn-primary.disabled:focus,.btn-primary[disabled]:focus,fieldset[disabled] .btn-primary:focus,.btn-primary.disabled.focus,.btn-primary[disabled].focus,fieldset[disabled] .btn-primary.focus,.btn-primary.disabled:active,.btn-primary[disabled]:active,fieldset[disabled] .btn-primary:active,.btn-primary.disabled.active,.btn-primary[disabled].active,fieldset[disabled] .btn-primary.active{background-color:#337ab7;border-color:#2e6da4}.btn-primary .badge{color:#337ab7;background-color:#fff}.btn-success{color:#fff;background-color:#5cb85c;border-color:#4cae4c}.btn-success:hover,.btn-success:focus,.btn-success.focus,.btn-success:active,.btn-success.active,.open>.dropdown-toggle.btn-success{color:#fff;background-color:#449d44;border-color:#398439}.btn-success:active,.btn-success.active,.open>.dropdown-toggle.btn-success{background-image:none}.btn-success.disabled,.btn-success[disabled],fieldset[disabled] .btn-success,.btn-success.disabled:hover,.btn-success[disabled]:hover,fieldset[disabled] .btn-success:hover,.btn-success.disabled:focus,.btn-success[disabled]:focus,fieldset[disabled] .btn-success:focus,.btn-success.disabled.focus,.btn-success[disabled].focus,fieldset[disabled] .btn-success.focus,.btn-success.disabled:active,.btn-success[disabled]:active,fieldset[disabled] .btn-success:active,.btn-success.disabled.active,.btn-success[disabled].active,fieldset[disabled] .btn-success.active{background-color:#5cb85c;border-color:#4cae4c}.btn-success .badge{color:#5cb85c;background-color:#fff}.btn-info{color:#fff;background-color:#5bc0de;border-color:#46b8da}.btn-info:hover,.btn-info:focus,.btn-info.focus,.btn-info:active,.btn-info.active,.open>.dropdown-toggle.btn-info{color:#fff;background-color:#31b0d5;border-color:#269abc}.btn-info:active,.btn-info.active,.open>.dropdown-toggle.btn-info{background-image:none}.btn-info.disabled,.btn-info[disabled],fieldset[disabled] .btn-info,.btn-info.disabled:hover,.btn-info[disabled]:hover,fieldset[disabled] .btn-info:hover,.btn-info.disabled:focus,.btn-info[disabled]:focus,fieldset[disabled] .btn-info:focus,.btn-info.disabled.focus,.btn-info[disabled].focus,fieldset[disabled] .btn-info.focus,.btn-info.disabled:active,.btn-info[disabled]:active,fieldset[disabled] .btn-info:active,.btn-info.disabled.active,.btn-info[disabled].active,fieldset[disabled] .btn-info.active{background-color:#5bc0de;border-color:#46b8da}.btn-info .badge{color:#5bc0de;background-color:#fff}.btn-warning{color:#fff;background-color:#f0ad4e;border-color:#eea236}.btn-warning:hover,.btn-warning:focus,.btn-warning.focus,.btn-warning:active,.btn-warning.active,.open>.dropdown-toggle.btn-warning{color:#fff;background-color:#ec971f;border-color:#d58512}.btn-warning:active,.btn-warning.active,.open>.dropdown-toggle.btn-warning{background-image:none}.btn-warning.disabled,.btn-warning[disabled],fieldset[disabled] .btn-warning,.btn-warning.disabled:hover,.btn-warning[disabled]:hover,fieldset[disabled] .btn-warning:hover,.btn-warning.disabled:focus,.btn-warning[disabled]:focus,fieldset[disabled] .btn-warning:focus,.btn-warning.disabled.focus,.btn-warning[disabled].focus,fieldset[disabled] .btn-warning.focus,.btn-warning.disabled:active,.btn-warning[disabled]:active,fieldset[disabled] .btn-warning:active,.btn-warning.disabled.active,.btn-warning[disabled].active,fieldset[disabled] .btn-warning.active{background-color:#f0ad4e;border-color:#eea236}.btn-warning .badge{color:#f0ad4e;background-color:#fff}.btn-danger{color:#fff;background-color:#d9534f;border-color:#d43f3a}.btn-danger:hover,.btn-danger:focus,.btn-danger.focus,.btn-danger:active,.btn-danger.active,.open>.dropdown-toggle.btn-danger{color:#fff;background-color:#c9302c;border-color:#ac2925}.btn-danger:active,.btn-danger.active,.open>.dropdown-toggle.btn-danger{background-image:none}.btn-danger.disabled,.btn-danger[disabled],fieldset[disabled] .btn-danger,.btn-danger.disabled:hover,.btn-danger[disabled]:hover,fieldset[disabled] .btn-danger:hover,.btn-danger.disabled:focus,.btn-danger[disabled]:focus,fieldset[disabled] .btn-danger:focus,.btn-danger.disabled.focus,.btn-danger[disabled].focus,fieldset[disabled] .btn-danger.focus,.btn-danger.disabled:active,.btn-danger[disabled]:active,fieldset[disabled] .btn-danger:active,.btn-danger.disabled.active,.btn-danger[disabled].active,fieldset[disabled] .btn-danger.active{background-color:#d9534f;border-color:#d43f3a}.btn-danger .badge{color:#d9534f;background-color:#fff}.btn-link{color:#337ab7;font-weight:normal;border-radius:0}.btn-link,.btn-link:active,.btn-link.active,.btn-link[disabled],fieldset[disabled] .btn-link{background-color:transparent;-webkit-box-shadow:none;box-shadow:none}.btn-link,.btn-link:hover,.btn-link:focus,.btn-link:active{border-color:transparent}.btn-link:hover,.btn-link:focus{color:#23527c;text-decoration:underline;background-color:transparent}.btn-link[disabled]:hover,fieldset[disabled] .btn-link:hover,.btn-link[disabled]:focus,fieldset[disabled] .btn-link:focus{color:#777;text-decoration:none}.btn-lg{padding:10px 16px;font-size:18px;line-height:1.3333333;border-radius:6px}.btn-sm{padding:5px 10px;font-size:12px;line-height:1.5;border-radius:3px}.btn-xs{padding:1px 5px;font-size:12px;line-height:1.5;border-radius:3px}.btn-block{display:block;width:100%}.btn-block+.btn-block{margin-top:5px}input[type="submit"].btn-block,input[type="reset"].btn-block,input[type="button"].btn-block{width:100%}.nav{margin-bottom:0;padding-left:0;list-style:none}.nav>li{position:relative;display:block}.nav>li>a{position:relative;display:block;padding:10px 15px}.nav>li>a:hover,.nav>li>a:focus{text-decoration:none;background-color:#eee}.nav>li.disabled>a{color:#777}.nav>li.disabled>a:hover,.nav>li.disabled>a:focus{color:#777;text-decoration:none;background-color:transparent;cursor:not-allowed}.nav .open>a,.nav .open>a:hover,.nav .open>a:focus{background-color:#eee;border-color:#337ab7}.nav .nav-divider{height:1px;margin:9px 0;overflow:hidden;background-color:#e5e5e5}.nav>li>a>img{max-width:none}.nav-tabs{border-bottom:1px solid #ddd}.nav-tabs>li{float:left;margin-bottom:-1px}.nav-tabs>li>a{margin-right:2px;line-height:1.42857143;border:1px solid transparent;border-radius:4px 4px 0 0}.nav-tabs>li>a:hover{border-color:#eee #eee #ddd}.nav-tabs>li.active>a,.nav-tabs>li.active>a:hover,.nav-tabs>li.active>a:focus{color:#555;background-color:#fff;border:1px solid #ddd;border-bottom-color:transparent;cursor:default}.nav-tabs.nav-justified{width:100%;border-bottom:0}.nav-tabs.nav-justified>li{float:none}.nav-tabs.nav-justified>li>a{text-align:center;margin-bottom:5px}.nav-tabs.nav-justified>.dropdown .dropdown-menu{top:auto;left:auto}@media (min-width:768px){.nav-tabs.nav-justified>li{display:table-cell;width:1%}.nav-tabs.nav-justified>li>a{margin-bottom:0}}.nav-tabs.nav-justified>li>a{margin-right:0;border-radius:4px}.nav-tabs.nav-justified>.active>a,.nav-tabs.nav-justified>.active>a:hover,.nav-tabs.nav-justified>.active>a:focus{border:1px solid #ddd}@media (min-width:768px){.nav-tabs.nav-justified>li>a{border-bottom:1px solid #ddd;border-radius:4px 4px 0 0}.nav-tabs.nav-justified>.active>a,.nav-tabs.nav-justified>.active>a:hover,.nav-tabs.nav-justified>.active>a:focus{border-bottom-color:#fff}}.nav-pills>li{float:left}.nav-pills>li>a{border-radius:4px}.nav-pills>li+li{margin-left:2px}.nav-pills>li.active>a,.nav-pills>li.active>a:hover,.nav-pills>li.active>a:focus{color:#fff;background-color:#337ab7}.nav-stacked>li{float:none}.nav-stacked>li+li{margin-top:2px;margin-left:0}.nav-justified{width:100%}.nav-justified>li{float:none}.nav-justified>li>a{text-align:center;margin-bottom:5px}.nav-justified>.dropdown .dropdown-menu{top:auto;left:auto}@media (min-width:768px){.nav-justified>li{display:table-cell;width:1%}.nav-justified>li>a{margin-bottom:0}}.nav-tabs-justified{border-bottom:0}.nav-tabs-justified>li>a{margin-right:0;border-radius:4px}.nav-tabs-justified>.active>a,.nav-tabs-justified>.active>a:hover,.nav-tabs-justified>.active>a:focus{border:1px solid #ddd}@media (min-width:768px){.nav-tabs-justified>li>a{border-bottom:1px solid #ddd;border-radius:4px 4px 0 0}.nav-tabs-justified>.active>a,.nav-tabs-justified>.active>a:hover,.nav-tabs-justified>.active>a:focus{border-bottom-color:#fff}}.tab-content>.tab-pane{display:none;visibility:hidden}.tab-content>.active{display:block;visibility:visible}.nav-tabs .dropdown-menu{margin-top:-1px;border-top-right-radius:0;border-top-left-radius:0}.navbar{position:relative;min-height:50px;margin-bottom:20px;border:1px solid transparent}@media (min-width:768px){.navbar{border-radius:4px}}@media (min-width:768px){.navbar-header{float:left}}.navbar-collapse{overflow-x:visible;padding-right:15px;padding-left:15px;border-top:1px solid transparent;-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,0.1);box-shadow:inset 0 1px 0 rgba(255,255,255,0.1);-webkit-overflow-scrolling:touch}.navbar-collapse.in{overflow-y:auto}@media (min-width:768px){.navbar-collapse{width:auto;border-top:0;-webkit-box-shadow:none;box-shadow:none}.navbar-collapse.collapse{display:block !important;visibility:visible !important;height:auto !important;padding-bottom:0;overflow:visible !important}.navbar-collapse.in{overflow-y:visible}.navbar-fixed-top .navbar-collapse,.navbar-static-top .navbar-collapse,.navbar-fixed-bottom .navbar-collapse{padding-left:0;padding-right:0}}.navbar-fixed-top .navbar-collapse,.navbar-fixed-bottom .navbar-collapse{max-height:340px}@media (max-device-width:480px) and (orientation:landscape){.navbar-fixed-top .navbar-collapse,.navbar-fixed-bottom .navbar-collapse{max-height:200px}}.container>.navbar-header,.container-fluid>.navbar-header,.container>.navbar-collapse,.container-fluid>.navbar-collapse{margin-right:-15px;margin-left:-15px}@media (min-width:768px){.container>.navbar-header,.container-fluid>.navbar-header,.container>.navbar-collapse,.container-fluid>.navbar-collapse{margin-right:0;margin-left:0}}.navbar-static-top{z-index:1000;border-width:0 0 1px}@media (min-width:768px){.navbar-static-top{border-radius:0}}.navbar-fixed-top,.navbar-fixed-bottom{position:fixed;right:0;left:0;z-index:1030}@media (min-width:768px){.navbar-fixed-top,.navbar-fixed-bottom{border-radius:0}}.navbar-fixed-top{top:0;border-width:0 0 1px}.navbar-fixed-bottom{bottom:0;margin-bottom:0;border-width:1px 0 0}.navbar-brand{float:left;padding:15px 15px;font-size:18px;line-height:20px;height:50px}.navbar-brand:hover,.navbar-brand:focus{text-decoration:none}.navbar-brand>img{display:block}@media (min-width:768px){.navbar>.container .navbar-brand,.navbar>.container-fluid .navbar-brand{margin-left:-15px}}.navbar-toggle{position:relative;float:right;margin-right:15px;padding:9px 10px;margin-top:8px;margin-bottom:8px;background-color:transparent;background-image:none;border:1px solid transparent;border-radius:4px}.navbar-toggle:focus{outline:0}.navbar-toggle .icon-bar{display:block;width:22px;height:2px;border-radius:1px}.navbar-toggle .icon-bar+.icon-bar{margin-top:4px}@media (min-width:768px){.navbar-toggle{display:none}}.navbar-nav{margin:7.5px -15px}.navbar-nav>li>a{padding-top:10px;padding-bottom:10px;line-height:20px}@media (max-width:767px){.navbar-nav .open .dropdown-menu{position:static;float:none;width:auto;margin-top:0;background-color:transparent;border:0;-webkit-box-shadow:none;box-shadow:none}.navbar-nav .open .dropdown-menu>li>a,.navbar-nav .open .dropdown-menu .dropdown-header{padding:5px 15px 5px 25px}.navbar-nav .open .dropdown-menu>li>a{line-height:20px}.navbar-nav .open .dropdown-menu>li>a:hover,.navbar-nav .open .dropdown-menu>li>a:focus{background-image:none}}@media (min-width:768px){.navbar-nav{float:left;margin:0}.navbar-nav>li{float:left}.navbar-nav>li>a{padding-top:15px;padding-bottom:15px}}.navbar-form{margin-left:-15px;margin-right:-15px;padding:10px 15px;border-top:1px solid transparent;border-bottom:1px solid transparent;-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,0.1),0 1px 0 rgba(255,255,255,0.1);box-shadow:inset 0 1px 0 rgba(255,255,255,0.1),0 1px 0 rgba(255,255,255,0.1);margin-top:8px;margin-bottom:8px}@media (min-width:768px){.navbar-form .form-group{display:inline-block;margin-bottom:0;vertical-align:middle}.navbar-form .form-control{display:inline-block;width:auto;vertical-align:middle}.navbar-form .form-control-static{display:inline-block}.navbar-form .input-group{display:inline-table;vertical-align:middle}.navbar-form .input-group .input-group-addon,.navbar-form .input-group .input-group-btn,.navbar-form .input-group .form-control{width:auto}.navbar-form .input-group>.form-control{width:100%}.navbar-form .control-label{margin-bottom:0;vertical-align:middle}.navbar-form .radio,.navbar-form .checkbox{display:inline-block;margin-top:0;margin-bottom:0;vertical-align:middle}.navbar-form .radio label,.navbar-form .checkbox label{padding-left:0}.navbar-form .radio input[type="radio"],.navbar-form .checkbox input[type="checkbox"]{position:relative;margin-left:0}.navbar-form .has-feedback .form-control-feedback{top:0}}@media (max-width:767px){.navbar-form .form-group{margin-bottom:5px}.navbar-form .form-group:last-child{margin-bottom:0}}@media (min-width:768px){.navbar-form{width:auto;border:0;margin-left:0;margin-right:0;padding-top:0;padding-bottom:0;-webkit-box-shadow:none;box-shadow:none}}.navbar-nav>li>.dropdown-menu{margin-top:0;border-top-right-radius:0;border-top-left-radius:0}.navbar-fixed-bottom .navbar-nav>li>.dropdown-menu{margin-bottom:0;border-top-right-radius:4px;border-top-left-radius:4px;border-bottom-right-radius:0;border-bottom-left-radius:0}.navbar-btn{margin-top:8px;margin-bottom:8px}.navbar-btn.btn-sm{margin-top:10px;margin-bottom:10px}.navbar-btn.btn-xs{margin-top:14px;margin-bottom:14px}.navbar-text{margin-top:15px;margin-bottom:15px}@media (min-width:768px){.navbar-text{float:left;margin-left:15px;margin-right:15px}}@media (min-width:768px){.navbar-left{float:left !important}.navbar-right{float:right !important;margin-right:-15px}.navbar-right~.navbar-right{margin-right:0}}.navbar-default{background-color:#f8f8f8;border-color:#e7e7e7}.navbar-default .navbar-brand{color:#777}.navbar-default .navbar-brand:hover,.navbar-default .navbar-brand:focus{color:#5e5e5e;background-color:transparent}.navbar-default .navbar-text{color:#777}.navbar-default .navbar-nav>li>a{color:#777}.navbar-default .navbar-nav>li>a:hover,.navbar-default .navbar-nav>li>a:focus{color:#333;background-color:transparent}.navbar-default .navbar-nav>.active>a,.navbar-default .navbar-nav>.active>a:hover,.navbar-default .navbar-nav>.active>a:focus{color:#555;background-color:#e7e7e7}.navbar-default .navbar-nav>.disabled>a,.navbar-default .navbar-nav>.disabled>a:hover,.navbar-default .navbar-nav>.disabled>a:focus{color:#ccc;background-color:transparent}.navbar-default .navbar-toggle{border-color:#ddd}.navbar-default .navbar-toggle:hover,.navbar-default .navbar-toggle:focus{background-color:#ddd}.navbar-default .navbar-toggle .icon-bar{background-color:#888}.navbar-default .navbar-collapse,.navbar-default .navbar-form{border-color:#e7e7e7}.navbar-default .navbar-nav>.open>a,.navbar-default .navbar-nav>.open>a:hover,.navbar-default .navbar-nav>.open>a:focus{background-color:#e7e7e7;color:#555}@media (max-width:767px){.navbar-default .navbar-nav .open .dropdown-menu>li>a{color:#777}.navbar-default .navbar-nav .open .dropdown-menu>li>a:hover,.navbar-default .navbar-nav .open .dropdown-menu>li>a:focus{color:#333;background-color:transparent}.navbar-default .navbar-nav .open .dropdown-menu>.active>a,.navbar-default .navbar-nav .open .dropdown-menu>.active>a:hover,.navbar-default .navbar-nav .open .dropdown-menu>.active>a:focus{color:#555;background-color:#e7e7e7}.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a,.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a:hover,.navbar-default .navbar-nav .open .dropdown-menu>.disabled>a:focus{color:#ccc;background-color:transparent}}.navbar-default .navbar-link{color:#777}.navbar-default .navbar-link:hover{color:#333}.navbar-default .btn-link{color:#777}.navbar-default .btn-link:hover,.navbar-default .btn-link:focus{color:#333}.navbar-default .btn-link[disabled]:hover,fieldset[disabled] .navbar-default .btn-link:hover,.navbar-default .btn-link[disabled]:focus,fieldset[disabled] .navbar-default .btn-link:focus{color:#ccc}.navbar-inverse{background-color:#222;border-color:#080808}.navbar-inverse .navbar-brand{color:#9d9d9d}.navbar-inverse .navbar-brand:hover,.navbar-inverse .navbar-brand:focus{color:#fff;background-color:transparent}.navbar-inverse .navbar-text{color:#9d9d9d}.navbar-inverse .navbar-nav>li>a{color:#9d9d9d}.navbar-inverse .navbar-nav>li>a:hover,.navbar-inverse .navbar-nav>li>a:focus{color:#fff;background-color:transparent}.navbar-inverse .navbar-nav>.active>a,.navbar-inverse .navbar-nav>.active>a:hover,.navbar-inverse .navbar-nav>.active>a:focus{color:#fff;background-color:#080808}.navbar-inverse .navbar-nav>.disabled>a,.navbar-inverse .navbar-nav>.disabled>a:hover,.navbar-inverse .navbar-nav>.disabled>a:focus{color:#444;background-color:transparent}.navbar-inverse .navbar-toggle{border-color:#333}.navbar-inverse .navbar-toggle:hover,.navbar-inverse .navbar-toggle:focus{background-color:#333}.navbar-inverse .navbar-toggle .icon-bar{background-color:#fff}.navbar-inverse .navbar-collapse,.navbar-inverse .navbar-form{border-color:#101010}.navbar-inverse .navbar-nav>.open>a,.navbar-inverse .navbar-nav>.open>a:hover,.navbar-inverse .navbar-nav>.open>a:focus{background-color:#080808;color:#fff}@media (max-width:767px){.navbar-inverse .navbar-nav .open .dropdown-menu>.dropdown-header{border-color:#080808}.navbar-inverse .navbar-nav .open .dropdown-menu .divider{background-color:#080808}.navbar-inverse .navbar-nav .open .dropdown-menu>li>a{color:#9d9d9d}.navbar-inverse .navbar-nav .open .dropdown-menu>li>a:hover,.navbar-inverse .navbar-nav .open .dropdown-menu>li>a:focus{color:#fff;background-color:transparent}.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a,.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a:hover,.navbar-inverse .navbar-nav .open .dropdown-menu>.active>a:focus{color:#fff;background-color:#080808}.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a,.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a:hover,.navbar-inverse .navbar-nav .open .dropdown-menu>.disabled>a:focus{color:#444;background-color:transparent}}.navbar-inverse .navbar-link{color:#9d9d9d}.navbar-inverse .navbar-link:hover{color:#fff}.navbar-inverse .btn-link{color:#9d9d9d}.navbar-inverse .btn-link:hover,.navbar-inverse .btn-link:focus{color:#fff}.navbar-inverse .btn-link[disabled]:hover,fieldset[disabled] .navbar-inverse .btn-link:hover,.navbar-inverse .btn-link[disabled]:focus,fieldset[disabled] .navbar-inverse .btn-link:focus{color:#444}.clearfix:before,.clearfix:after,.dl-horizontal dd:before,.dl-horizontal dd:after,.container:before,.container:after,.container-fluid:before,.container-fluid:after,.row:before,.row:after,.form-horizontal .form-group:before,.form-horizontal .form-group:after,.nav:before,.nav:after,.navbar:before,.navbar:after,.navbar-header:before,.navbar-header:after,.navbar-collapse:before,.navbar-collapse:after{content:" ";display:table}.clearfix:after,.dl-horizontal dd:after,.container:after,.container-fluid:after,.row:after,.form-horizontal .form-group:after,.nav:after,.navbar:after,.navbar-header:after,.navbar-collapse:after{clear:both}.center-block{display:block;margin-left:auto;margin-right:auto}.pull-right{float:right !important}.pull-left{float:left !important}.hide{display:none !important}.show{display:block !important}.invisible{visibility:hidden}.text-hide{font:0/0 a;color:transparent;text-shadow:none;background-color:transparent;border:0}.hidden{display:none !important;visibility:hidden !important}.affix{position:fixed}@-ms-viewport{width:device-width}.visible-xs,.visible-sm,.visible-md,.visible-lg{display:none !important}.visible-xs-block,.visible-xs-inline,.visible-xs-inline-block,.visible-sm-block,.visible-sm-inline,.visible-sm-inline-block,.visible-md-block,.visible-md-inline,.visible-md-inline-block,.visible-lg-block,.visible-lg-inline,.visible-lg-inline-block{display:none !important}@media (max-width:767px){.visible-xs{display:block !important}table.visible-xs{display:table}tr.visible-xs{display:table-row !important}th.visible-xs,td.visible-xs{display:table-cell !important}}@media (max-width:767px){.visible-xs-block{display:block !important}}@media (max-width:767px){.visible-xs-inline{display:inline !important}}@media (max-width:767px){.visible-xs-inline-block{display:inline-block !important}}@media (min-width:768px) and (max-width:991px){.visible-sm{display:block !important}table.visible-sm{display:table}tr.visible-sm{display:table-row !important}th.visible-sm,td.visible-sm{display:table-cell !important}}@media (min-width:768px) and (max-width:991px){.visible-sm-block{display:block !important}}@media (min-width:768px) and (max-width:991px){.visible-sm-inline{display:inline !important}}@media (min-width:768px) and (max-width:991px){.visible-sm-inline-block{display:inline-block !important}}@media (min-width:992px) and (max-width:1199px){.visible-md{display:block !important}table.visible-md{display:table}tr.visible-md{display:table-row !important}th.visible-md,td.visible-md{display:table-cell !important}}@media (min-width:992px) and (max-width:1199px){.visible-md-block{display:block !important}}@media (min-width:992px) and (max-width:1199px){.visible-md-inline{display:inline !important}}@media (min-width:992px) and (max-width:1199px){.visible-md-inline-block{display:inline-block !important}}@media (min-width:1200px){.visible-lg{display:block !important}table.visible-lg{display:table}tr.visible-lg{display:table-row !important}th.visible-lg,td.visible-lg{display:table-cell !important}}@media (min-width:1200px){.visible-lg-block{display:block !important}}@media (min-width:1200px){.visible-lg-inline{display:inline !important}}@media (min-width:1200px){.visible-lg-inline-block{display:inline-block !important}}@media (max-width:767px){.hidden-xs{display:none !important}}@media (min-width:768px) and (max-width:991px){.hidden-sm{display:none !important}}@media (min-width:992px) and (max-width:1199px){.hidden-md{display:none !important}}@media (min-width:1200px){.hidden-lg{display:none !important}}.visible-print{display:none !important}@media print{.visible-print{display:block !important}table.visible-print{display:table}tr.visible-print{display:table-row !important}th.visible-print,td.visible-print{display:table-cell !important}}.visible-print-block{display:none !important}@media print{.visible-print-block{display:block !important}}.visible-print-inline{display:none !important}@media print{.visible-print-inline{display:inline !important}}.visible-print-inline-block{display:none !important}@media print{.visible-print-inline-block{display:inline-block !important}}@media print{.hidden-print{display:none !important}} diff --git a/www/css/gettor.css b/www/css/gettor.css deleted file mode 100644 index 520357a73aaee6c3ee3d972587fe88bbb47f7175..0000000000000000000000000000000000000000 --- a/www/css/gettor.css +++ /dev/null @@ -1,83 +0,0 @@ -/* Fonts */ -@font-face { - font-family: 'Lato'; - font-style: normal; - font-weight: 400; - src: local('Lato Regular'), local('Lato-Regular'), url('../fonts/lato-regular.woff') format('woff'); -} -@font-face { - font-family: 'Lato'; - font-style: normal; - font-weight: 700; - src: local('Lato Bold'), local('Lato-Bold'), url('../fonts/lato-bold.woff') format('woff'); -} -@font-face { - font-family: 'Lato'; - font-style: italic; - font-weight: 400; - src: local('Lato Italic'), local('Lato-Italic'), url('../fonts/lato-italic.woff') format('woff'); -} - -body { - padding-bottom: 20px; - /*background-color: #4ba027;*/ -} - -footer { - color: #aaa; -} - -a:link, a:visited { - color: #AF02D7; - text-decoration: none; -} - -a:hover { - color: #65007D; -} - -#main { - background-color: #fff; - margin: 5% 0; - font-family: "Lato"; - font-size: 16px; - font-weight: lighter; -} - -#main h2 { - color: #8500A3; -} - -#head-title { - color: #fff !important; - font-size: 23px; -} - -#head-link { - text-align: right; -} - -#head-link a:link { - color: #ccc; -} - -#head-link a:hover { - color: #fff; - text-decoration: none; -} - -.navbar { - background-color: #770093 !important; -} - -.pad-big-left { - padding-left: 110px; -} - -.pad-big-right { - padding-right: 110px; -} - -.big-link { - font-size: 26px; -} diff --git a/www/fonts/glyphicons-halflings-regular.eot b/www/fonts/glyphicons-halflings-regular.eot deleted file mode 100644 index b93a4953fff68df523aa7656497ee339d6026d64..0000000000000000000000000000000000000000 Binary files a/www/fonts/glyphicons-halflings-regular.eot and /dev/null differ diff --git a/www/fonts/glyphicons-halflings-regular.svg b/www/fonts/glyphicons-halflings-regular.svg deleted file mode 100644 index 94fb5490a2ed10b2c69a4a567a4fd2e4f706d841..0000000000000000000000000000000000000000 --- a/www/fonts/glyphicons-halflings-regular.svg +++ /dev/null @@ -1,288 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/www/fonts/glyphicons-halflings-regular.ttf b/www/fonts/glyphicons-halflings-regular.ttf deleted file mode 100644 index 1413fc609ab6f21774de0cb7e01360095584f65b..0000000000000000000000000000000000000000 Binary files a/www/fonts/glyphicons-halflings-regular.ttf and /dev/null differ diff --git a/www/fonts/glyphicons-halflings-regular.woff b/www/fonts/glyphicons-halflings-regular.woff deleted file mode 100644 index 9e612858f802245ddcbf59788a0db942224bab35..0000000000000000000000000000000000000000 Binary files a/www/fonts/glyphicons-halflings-regular.woff and /dev/null differ diff --git a/www/fonts/glyphicons-halflings-regular.woff2 b/www/fonts/glyphicons-halflings-regular.woff2 deleted file mode 100644 index 64539b54c3751a6d9adb44c8e3a45ba5a73b77f0..0000000000000000000000000000000000000000 Binary files a/www/fonts/glyphicons-halflings-regular.woff2 and /dev/null differ diff --git a/www/fonts/lato-bold.woff b/www/fonts/lato-bold.woff deleted file mode 100644 index 4b1725113039be702aa9959edef8ca84560ed3a3..0000000000000000000000000000000000000000 Binary files a/www/fonts/lato-bold.woff and /dev/null differ diff --git a/www/fonts/lato-italic.woff b/www/fonts/lato-italic.woff deleted file mode 100644 index 09cc3791d5c1a03b5b34cf20a396151799a1e311..0000000000000000000000000000000000000000 Binary files a/www/fonts/lato-italic.woff and /dev/null differ diff --git a/www/fonts/lato-regular.woff b/www/fonts/lato-regular.woff deleted file mode 100644 index f48e48487c018f5d4a5aa8175cc96deeb101aa31..0000000000000000000000000000000000000000 Binary files a/www/fonts/lato-regular.woff and /dev/null differ diff --git a/www/img/android-logo.png b/www/img/android-logo.png deleted file mode 100644 index 624384e9624ff484667da81a7ff5155e6d3d8357..0000000000000000000000000000000000000000 Binary files a/www/img/android-logo.png and /dev/null differ diff --git a/www/img/gettor-logo.png b/www/img/gettor-logo.png deleted file mode 100644 index 525d8d05f25f6aa542a3f9345f46da036c09efe2..0000000000000000000000000000000000000000 Binary files a/www/img/gettor-logo.png and /dev/null differ diff --git a/www/img/linux-logo.png b/www/img/linux-logo.png deleted file mode 100644 index f6d6fd9537b1d702c02adc2de6255d489ba1470c..0000000000000000000000000000000000000000 Binary files a/www/img/linux-logo.png and /dev/null differ diff --git a/www/img/osx-logo.png b/www/img/osx-logo.png deleted file mode 100644 index 1e19dca6f32a91b023213a6fad50a81f428b57f3..0000000000000000000000000000000000000000 Binary files a/www/img/osx-logo.png and /dev/null differ diff --git a/www/img/windows-logo.png b/www/img/windows-logo.png deleted file mode 100644 index 01f273de87b07b99d9055344a782e19018d45cfb..0000000000000000000000000000000000000000 Binary files a/www/img/windows-logo.png and /dev/null differ diff --git a/www/index.html b/www/index.html deleted file mode 100644 index a4d7af823605d88d377ae2b14f73078431d9af55..0000000000000000000000000000000000000000 --- a/www/index.html +++ /dev/null @@ -1 +0,0 @@ - GetTor | Download Tor Browser for Windows, Linux, OS X

Download Tor Browser


Below you will find links to download the latest version of Tor Browser (5.5.2).


Direct downloads

Tor Browser for Windows
English, Farsi, Chinese, Turkish
Tor Browser for OS X
English, Farsi, Chinese, Turkish
Tor Browser for Linux 32-bit
English, Farsi, Chinese, Turkish
Tor Browser for Linux 64-bit
English, Farsi, Chinese, Turkish

Alternative downloads

Get links via Email: You can send an email to gettor@torproject.org. Send the word help in the body of the message to learn how to interact with it.
Get links via XMPP: You can send a message to get_tor@riseup.net using your favorite XMPP client. Simply enter help in an XMPP message to learn how to interact with it.
Get links via Twitter: You can send a direct message to @get_tor account (you don't need to follow). Send the word help in a direct message to learn how to interact with it.

Get bridges

Bridges are Tor relays that help you circumvent censorship. If you suspect your access to the Tor network is being blocked, you may want to use bridges. You can get bridges from the HTTP distributor. You can also send an email to bridges@torproject.org (please note that you must send the email using an address from one of the following email providers: riseup, gmail or yahoo).

\ No newline at end of file