├── pylinktester ├── readme.md ├── core │ ├── __init__.py │ ├── bfs.pyc │ ├── test.pyc │ ├── __init__.pyc │ ├── bfs.py │ └── test.py ├── model │ ├── __init__.py │ ├── urlSync.pyc │ ├── __init__.pyc │ ├── urlQuence.pyc │ ├── urlSync.py │ └── urlQuence.py ├── threads │ ├── __init__.py │ ├── __init__.pyc │ ├── testThread.pyc │ ├── spliderThread.pyc │ ├── threadController.pyc │ ├── testThread.py │ ├── spliderThread.py │ └── threadController.py ├── utils │ ├── __init__.py │ ├── getUrls.pyc │ ├── __init__.pyc │ ├── testUrls.pyc │ ├── getRequest.pyc │ ├── getUrls.py │ ├── testUrls.py │ └── getRequest.py ├── .gitignore ├── main.py └── logs │ └── 2014-02-08.txt ├── sphinx ├── _build │ ├── html │ │ ├── objects.inv │ │ ├── _static │ │ │ ├── down.png │ │ │ ├── file.png │ │ │ ├── plus.png │ │ │ ├── up.png │ │ │ ├── minus.png │ │ │ ├── comment.png │ │ │ ├── ajax-loader.gif │ │ │ ├── up-pressed.png │ │ │ ├── comment-bright.png │ │ │ ├── comment-close.png │ │ │ ├── down-pressed.png │ │ │ ├── pygments.css │ │ │ ├── default.css │ │ │ ├── sidebar.js │ │ │ ├── doctools.js │ │ │ ├── underscore.js │ │ │ ├── basic.css │ │ │ ├── searchtools.js │ │ │ ├── websupport.js │ │ │ └── jquery.js │ │ ├── searchindex.js │ │ ├── .buildinfo │ │ ├── _sources │ │ │ └── index.txt │ │ ├── genindex.html │ │ ├── search.html │ │ └── index.html │ └── doctrees │ │ ├── index.doctree │ │ └── environment.pickle ├── index.rst ├── make.bat ├── Makefile └── conf.py ├── .gitignore └── README.md /pylinktester/readme.md: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /pylinktester/core/__init__.py: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /pylinktester/model/__init__.py: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /pylinktester/threads/__init__.py: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /pylinktester/utils/__init__.py: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /pylinktester/core/bfs.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/core/bfs.pyc -------------------------------------------------------------------------------- /pylinktester/core/test.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/core/test.pyc -------------------------------------------------------------------------------- /pylinktester/core/__init__.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/core/__init__.pyc -------------------------------------------------------------------------------- /pylinktester/model/urlSync.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/model/urlSync.pyc -------------------------------------------------------------------------------- /pylinktester/utils/getUrls.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/utils/getUrls.pyc -------------------------------------------------------------------------------- /sphinx/_build/html/objects.inv: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/html/objects.inv -------------------------------------------------------------------------------- /pylinktester/model/__init__.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/model/__init__.pyc -------------------------------------------------------------------------------- /pylinktester/model/urlQuence.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/model/urlQuence.pyc -------------------------------------------------------------------------------- /pylinktester/utils/__init__.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/utils/__init__.pyc -------------------------------------------------------------------------------- /pylinktester/utils/testUrls.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/utils/testUrls.pyc -------------------------------------------------------------------------------- /pylinktester/threads/__init__.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/threads/__init__.pyc -------------------------------------------------------------------------------- /pylinktester/threads/testThread.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/threads/testThread.pyc -------------------------------------------------------------------------------- /pylinktester/utils/getRequest.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/utils/getRequest.pyc -------------------------------------------------------------------------------- /sphinx/_build/html/_static/down.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/html/_static/down.png -------------------------------------------------------------------------------- /sphinx/_build/html/_static/file.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/html/_static/file.png -------------------------------------------------------------------------------- /sphinx/_build/html/_static/plus.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/html/_static/plus.png -------------------------------------------------------------------------------- /sphinx/_build/html/_static/up.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/html/_static/up.png -------------------------------------------------------------------------------- /sphinx/_build/doctrees/index.doctree: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/doctrees/index.doctree -------------------------------------------------------------------------------- /sphinx/_build/html/_static/minus.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/html/_static/minus.png -------------------------------------------------------------------------------- /pylinktester/threads/spliderThread.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/threads/spliderThread.pyc -------------------------------------------------------------------------------- /sphinx/_build/html/_static/comment.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/html/_static/comment.png -------------------------------------------------------------------------------- /pylinktester/threads/threadController.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/pylinktester/threads/threadController.pyc -------------------------------------------------------------------------------- /sphinx/_build/doctrees/environment.pickle: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/doctrees/environment.pickle -------------------------------------------------------------------------------- /sphinx/_build/html/_static/ajax-loader.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/html/_static/ajax-loader.gif -------------------------------------------------------------------------------- /sphinx/_build/html/_static/up-pressed.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/html/_static/up-pressed.png -------------------------------------------------------------------------------- /sphinx/_build/html/_static/comment-bright.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/html/_static/comment-bright.png -------------------------------------------------------------------------------- /sphinx/_build/html/_static/comment-close.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/html/_static/comment-close.png -------------------------------------------------------------------------------- /sphinx/_build/html/_static/down-pressed.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Flowerowl/pylinktester/HEAD/sphinx/_build/html/_static/down-pressed.png -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | *~ 2 | *.log 3 | *.pyc 4 | .idea 5 | run 6 | build 7 | dist 8 | .project 9 | .pydevproject 10 | atlassian-ide-plugin.xml 11 | build 12 | dist 13 | *.egg-info 14 | logs 15 | .noseids 16 | .coverage 17 | cover 18 | install 19 | .env 20 | -------------------------------------------------------------------------------- /sphinx/_build/html/searchindex.js: -------------------------------------------------------------------------------- 1 | Search.setIndex({objects:{},terms:{index:0,search:0,pylinktest:0,welcom:0,modul:0,indic:0,content:0,tabl:0,document:0,page:0},objtypes:{},titles:["Welcome to pylinktester’s documentation!"],objnames:{},filenames:["index"]}) -------------------------------------------------------------------------------- /sphinx/_build/html/.buildinfo: -------------------------------------------------------------------------------- 1 | # Sphinx build info version 1 2 | # This file hashes the configuration used when building these files. When it is not found, a full rebuild will be done. 3 | config: 6175db360de31d3f40617f547ccd3764 4 | tags: fbb0d17656682115ca4d033fb2f83ba1 5 | -------------------------------------------------------------------------------- /sphinx/index.rst: -------------------------------------------------------------------------------- 1 | .. pylinktester documentation master file, created by 2 | sphinx-quickstart on Tue Nov 19 16:56:57 2013. 3 | You can adapt this file completely to your liking, but it should at least 4 | contain the root `toctree` directive. 5 | 6 | Welcome to pylinktester's documentation! 7 | ======================================== 8 | 9 | Contents: 10 | 11 | .. toctree:: 12 | :maxdepth: 2 13 | 14 | 15 | 16 | Indices and tables 17 | ================== 18 | 19 | * :ref:`genindex` 20 | * :ref:`modindex` 21 | * :ref:`search` 22 | 23 | -------------------------------------------------------------------------------- /sphinx/_build/html/_sources/index.txt: -------------------------------------------------------------------------------- 1 | .. pylinktester documentation master file, created by 2 | sphinx-quickstart on Tue Nov 19 16:56:57 2013. 3 | You can adapt this file completely to your liking, but it should at least 4 | contain the root `toctree` directive. 5 | 6 | Welcome to pylinktester's documentation! 7 | ======================================== 8 | 9 | Contents: 10 | 11 | .. toctree:: 12 | :maxdepth: 2 13 | 14 | 15 | 16 | Indices and tables 17 | ================== 18 | 19 | * :ref:`genindex` 20 | * :ref:`modindex` 21 | * :ref:`search` 22 | 23 | -------------------------------------------------------------------------------- /pylinktester/.gitignore: -------------------------------------------------------------------------------- 1 | .idea 2 | 3 | # https://github.com/github/gitignore/blob/master/Python.gitignore 4 | *.py[cod] 5 | 6 | # C extensions 7 | *.so 8 | 9 | # Packages 10 | *.egg 11 | *.egg-info 12 | dist 13 | build 14 | eggs 15 | parts 16 | bin 17 | var 18 | sdist 19 | develop-eggs 20 | .installed.cfg 21 | lib 22 | lib64 23 | __pycache__ 24 | 25 | # Installer logs 26 | pip-log.txt 27 | 28 | # Unit test / coverage reports 29 | .coverage 30 | .tox 31 | nosetests.xml 32 | 33 | # Translations 34 | *.mo 35 | 36 | # Mr Developer 37 | .mr.developer.cfg 38 | .project 39 | .pydevproject 40 | 41 | mcms/db.sqlite3 42 | -------------------------------------------------------------------------------- /pylinktester/main.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | import model.urlQuence as urlQuence 4 | import threads.threadController as tc 5 | import model.urlSync as urlSync 6 | 7 | 8 | if __name__=="__main__": 9 | seed = set(["http://m.sohu.com"]) #初始url,算作第一层链接 10 | threadNumber = 10 #线程数 11 | deepth = 5 #设置爬取深度 12 | urlQuence = urlQuence.urlQuence(deepth+1) #初始化deepth个set,存放相应层数未访问链接 13 | urlQuence.addUnvisitedUrl(seed, 1) #seed链接算作第一层 14 | urlSync = urlSync.urlSync() #为testThread同步未访问的url集合 15 | tc = tc.threadController(threadNumber, urlQuence, urlSync, deepth) #初始化线程管理器 16 | tc.start() 17 | -------------------------------------------------------------------------------- /pylinktester/threads/testThread.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | import threading 4 | import sys 5 | sys.path.insert(0, r'..') 6 | 7 | import core.test as core 8 | 9 | class testThread(threading.Thread): 10 | ''' 11 | 检测线程 12 | ''' 13 | 14 | def __init__(self, urlSync, spliderThreadPool, mutex): 15 | threading.Thread.__init__(self) 16 | self.setDaemon(True) 17 | #链接队列 18 | self.urlSync = urlSync 19 | #爬虫线程池,用来检测爬虫是否已死 20 | self.spliderThreadPool = spliderThreadPool 21 | self.mutex = mutex 22 | 23 | def run(self): 24 | core.test(self.urlSync, self.spliderThreadPool, self.mutex) 25 | -------------------------------------------------------------------------------- /pylinktester/threads/spliderThread.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | import threading 4 | import sys 5 | sys.path.insert(0, r'..') 6 | 7 | import core.bfs as core 8 | 9 | class spliderThread(threading.Thread): 10 | ''' 11 | 爬虫线程 12 | 采用广度优先算法 13 | ''' 14 | 15 | def __init__(self, urlQuence, urlSync, deepth, mutex): 16 | threading.Thread.__init__(self) 17 | self.setDaemon(True) 18 | #保存爬取链接的集合 19 | self.urlQuence = urlQuence 20 | #同时需要更新的供检测线程使用的队列 21 | self.urlSync = urlSync 22 | #爬取深度 23 | self.deepth = deepth 24 | self.mutex = mutex 25 | 26 | def run(self): 27 | core.bfs(self.urlQuence, self.urlSync, self.deepth, self.mutex) 28 | -------------------------------------------------------------------------------- /pylinktester/utils/getUrls.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | import urllib2 4 | import sys 5 | 6 | from bs4 import BeautifulSoup 7 | 8 | import testUrls 9 | import getRequest 10 | 11 | reload(sys) 12 | sys.setdefaultencoding("utf-8") 13 | 14 | def geturls(url): 15 | ''' 16 | 获取当前页所有链接 17 | ''' 18 | source = getsource(url) 19 | urlset = set() 20 | try: 21 | soup = BeautifulSoup(source) 22 | except: 23 | return urlset 24 | for link in soup.find_all('a'): 25 | if link.get('href') is not None and (link.get('href')[:4] \ 26 | == 'http' or link.get('href')[:1] == '/'): 27 | if link.get('href')[:4] == 'http': 28 | urlset.add(link.get('href')) 29 | if link.get('href')[:1] == '/': 30 | urlset.add('http://m.sohu.com'+link.get('href')) 31 | return urlset 32 | 33 | 34 | def getsource(url): 35 | ''' 36 | 获取当前网页源码 37 | ''' 38 | req, opener = getRequest.getRequest(url) 39 | try: 40 | urlopen = opener.open(req, timeout = 10) 41 | source = urlopen.read() 42 | return source 43 | except Exception: 44 | testUrls.testUrls(url) 45 | -------------------------------------------------------------------------------- /pylinktester/model/urlSync.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | 4 | import Queue 5 | 6 | class urlSync(): 7 | ''' 8 | 为检测线程创建一个队列,同时爬虫线程向此队列添加 9 | ''' 10 | 11 | def __init__(self): 12 | #链接队列 13 | self.urlQue = Queue.Queue() 14 | #已检测过的链接 15 | self.visited = set() 16 | #临时集合,用来去重 17 | self.tempSet = set() 18 | #获取未访问的链接 19 | def getUnvisitedUrl(self): 20 | try: 21 | return self.urlQue.get(block=True, timeout=2.0) 22 | except Exception, e: 23 | print "[EXCEPTION] getUnvisitedUrl() - EMPTY" 24 | return None 25 | #添加未访问的链接 26 | def addUnvisitedUrl(self, urls): 27 | self.tempSet.update(urls) 28 | for url in (self.tempSet - (self.tempSet & self.visited)): 29 | self.urlQue.put(url) 30 | self.tempSet.clear() 31 | #获取未访问链接数目 32 | def getUnvistedUrlCount(self): 33 | return self.urlQue.qsize() 34 | #获取已访问链接 35 | def getVisitedUrl(self): 36 | return self.visited 37 | #获取访问过的链接数目 38 | def getVisitedUrlCount(self): 39 | return len(self.visited) 40 | #添加已访问过的链接 41 | def addVisistedUrl(self, url): 42 | self.visited.add(url) 43 | -------------------------------------------------------------------------------- /pylinktester/core/bfs.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | import sys 4 | import threading 5 | sys.path.insert(0, r'..') 6 | 7 | import utils.getUrls as utils 8 | 9 | 10 | def bfs(urlQuence, urlSync, deepth, mutex): 11 | ''' 12 | 广度优先算法,按层提取/存放链接 13 | ''' 14 | 15 | current = urlQuence.getLayerunVisited() #当前未访问的最小层数 16 | while current is not None and current < deepth+1 : 17 | #从当前层提取一个未访问链接 18 | #print "bfs-mutex.acquire()..." 19 | mutex.acquire() 20 | #print "bfs-mutex.acquire() OK" 21 | visitUrl = urlQuence.unVisitedUrlDeQuence(current) 22 | mutex.release() 23 | #print "bfs-mutex.release() OK" 24 | print "第%d层未访问链接出队 \"%s\" "%(current, visitUrl) 25 | if visitUrl is None or visitUrl=="": 26 | break 27 | #获取超链接,set() 28 | links = utils.geturls(visitUrl) 29 | #将url放入已访问的url中 30 | urlQuence.addVisitedUrl(visitUrl) 31 | #未访问的url入列 32 | #print "bfs-2-mutex.acquire()..." 33 | mutex.acquire() 34 | #print "bfs-2-mutex.acquire() OK" 35 | urlQuence.addUnvisitedUrl(links, current+1) 36 | urlSync.addUnvisitedUrl(links) 37 | mutex.release() 38 | #print "bfs-2-mutex.release() OK" 39 | current = urlQuence.getLayerunVisited() 40 | -------------------------------------------------------------------------------- /pylinktester/core/test.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | import sys 4 | sys.path.insert(0, r'..') 5 | import threading 6 | 7 | import utils.testUrls as utils 8 | 9 | def test(urlSync, spliderThreadPool, mutex): 10 | ''' 11 | 检测链接的调度器 12 | ''' 13 | 14 | while urlSync.getUnvistedUrlCount() != 0 or spliderIsAlive(spliderThreadPool): 15 | #print "test-mutex.acquire()..." 16 | mutex.acquire() 17 | #print "test-mutex.acquire() OK" 18 | url = urlSync.getUnvisitedUrl() 19 | mutex.release() 20 | #print "test-mutex.release() OK" 21 | if url in urlSync.visited: 22 | continue 23 | if url is None: 24 | print '剩余链接数量',urlSync.getUnvistedUrlCount() 25 | for st in spliderThreadPool: 26 | print st.getName(),st.isAlive() 27 | continue 28 | print threading.currentThread() 29 | #检测链接 30 | utils.testUrls(url) 31 | #print "test-2-mutex.acquire()..." 32 | mutex.acquire() 33 | #print "test-2-mutex.acquire()OK" 34 | urlSync.addVisistedUrl(url) 35 | mutex.release() 36 | #print "test-2-mutex.release()OK" 37 | print '剩余链接数量',urlSync.getUnvistedUrlCount() 38 | 39 | def spliderIsAlive(spliderThreadPool): 40 | ''' 41 | 判断爬虫是否已死 42 | ''' 43 | 44 | for st in spliderThreadPool: 45 | if st.isAlive(): 46 | return True 47 | return False 48 | -------------------------------------------------------------------------------- /pylinktester/threads/threadController.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | import time 4 | import threading 5 | 6 | import spliderThread, testThread 7 | 8 | global g_mutex 9 | g_mutex = threading.Lock() 10 | 11 | class threadController: 12 | ''' 13 | 线程管理器,初始化爬虫/检测线程,运行完退出 14 | ''' 15 | 16 | def __init__(self, threadNumber, urlQuence, urlSync, deepth): 17 | self.threadNumber = threadNumber 18 | self.urlQuence = urlQuence 19 | self.urlSync = urlSync 20 | self.deepth = deepth 21 | self.spliderThreadPool = [] 22 | self.testThreadPool = [] 23 | self.mutex = g_mutex 24 | def start(self): 25 | for i in range(self.threadNumber): 26 | self.runSplider() 27 | if i == 0: #第一个爬虫需要爬一些预备链接供之后的爬虫使用 28 | time.sleep(10) 29 | #等待爬虫线程都开启之后再开启测试线程 30 | for i in range(self.threadNumber * 2): 31 | self.runTest() 32 | 33 | self.waitUntilEnd() 34 | 35 | def runSplider(self): 36 | st = spliderThread.spliderThread(self.urlQuence, self.urlSync, self.deepth, self.mutex) 37 | self.spliderThreadPool.append(st) 38 | st.start() 39 | 40 | def runTest(self): 41 | tt = testThread.testThread(self.urlSync, self.spliderThreadPool, self.mutex) 42 | self.testThreadPool.append(tt) 43 | tt.start() 44 | 45 | def waitUntilEnd(self): 46 | for st in self.spliderThreadPool: 47 | st.join() 48 | print "spliderThread[%s] 爬取完毕!" % st.getName() 49 | for tt in self.testThreadPool: 50 | tt.join() 51 | print "testThread[%s] 检测完毕!" % tt.getName() 52 | -------------------------------------------------------------------------------- /pylinktester/utils/testUrls.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | 4 | import urllib2 5 | import threading 6 | import os.path 7 | import time 8 | import socket 9 | 10 | import getRequest 11 | 12 | global g_mutex 13 | g_mutex = threading.Lock() 14 | 15 | def testUrls(url, repeat = 3): 16 | ''' 17 | 真正干活的检测链接函数,设置超时访问次数为三次 18 | ''' 19 | 20 | ti = time.strftime('%Y-%m-%d %H:%M:%S ',time.localtime(time.time())) 21 | if url is not None: 22 | req, opener = getRequest.getRequest(url) 23 | try: 24 | urlopen = opener.open(req, timeout = 10) 25 | except urllib2.HTTPError, ex: 26 | if(repeat > 0): 27 | testUrls(url, repeat - 1) 28 | else: 29 | log(str(ex), ti, url) 30 | except urllib2.URLError, ex: 31 | if(repeat > 0): 32 | testUrls(url, repeat - 1) 33 | else: 34 | log(str(ex), ti, url) 35 | except socket.timeout as ex: 36 | if(repeat > 0): 37 | testUrls(url, repeat - 1) 38 | else: 39 | log(str(ex), ti, url) 40 | 41 | 42 | def log(error, ti, url): 43 | ''' 44 | 记录日志 45 | ''' 46 | path = getLogsPath() 47 | print "log-mutex.acquire()..." 48 | g_mutex.acquire() 49 | print "log-mutex.acquire() OK" 50 | fileHandle = open (path+str(time.strftime('%Y-%m-%d'))+'.txt', 'a') 51 | fileHandle.write(ti+error+url+'\r\n') 52 | fileHandle.close() 53 | g_mutex.release() 54 | print "log-mutex.release() OK" 55 | 56 | 57 | def getLogsPath(): 58 | ''' 59 | 获取日志路径,若没有则创建 60 | ''' 61 | path = os.path.dirname(__file__) 62 | newpath = '/'.join(path.split('/')[:-1])+'/logs/' 63 | if(not os.path.exists(newpath)): 64 | os.mkdir(newpath) 65 | return newpath 66 | -------------------------------------------------------------------------------- /pylinktester/model/urlQuence.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | 4 | global uv 5 | 6 | class urlQuence: 7 | ''' 8 | 爬虫线程的链接保存集合,按层分配,一层一个set() 9 | ''' 10 | 11 | def __init__(self, deepth): 12 | #已访问的url集合 13 | self.visited=set() 14 | #设定爬去深度 15 | self.deepth = deepth 16 | #未访问的url字典,按层数做key 17 | self.unVisited = {} 18 | 19 | for i in range(self.deepth): 20 | self.unVisited[i+1] = set() 21 | 22 | #获取访问过的url集合 23 | def getVisitedUrl(self): 24 | return self.visited 25 | #获取未访问的url集合 26 | def getUnvisitedUrl(self): 27 | uv = set() 28 | for i, s in self.unVisited.items(): 29 | uv |= s 30 | return uv 31 | #添加到访问过得url队列中 32 | def addVisitedUrl(self, url): 33 | self.visited.add(url) 34 | #移除访问过得url 35 | def removeVisitedUrl(self, url): 36 | self.visited.remove(url) 37 | #按层提取未访问过得url 38 | def unVisitedUrlDeQuence(self, deepth): 39 | try: 40 | return self.unVisited[deepth].pop() 41 | except: 42 | return None 43 | #按层插入未访问url 44 | def addUnvisitedUrl(self, url, deepth): 45 | self.unVisited[deepth].update(url) 46 | #获得已访问的url数目 47 | def getVisitedUrlCount(self): 48 | return len(self.visited) 49 | #获得未访问的url数目 50 | def getUnvistedUrlCount(self): 51 | count = 0 52 | for i in range(self.deepth): 53 | count += len(self.unVisited[i+1]) 54 | return count 55 | #获取指定层数未访问链接数目 56 | def getUnvisitedUrlCountByDeepth(self, deepth): 57 | return len(self.unVisited[deepth]) 58 | #判断未访问的url集合是否为空,返回最小非空层 59 | def getLayerunVisited(self): 60 | for i in range(self.deepth): 61 | if len(self.unVisited[i+1]) != 0: 62 | return i+1 63 | 64 | 65 | -------------------------------------------------------------------------------- /pylinktester/utils/getRequest.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | from StringIO import StringIO 4 | import urllib2 5 | 6 | from gzip import GzipFile 7 | 8 | def getRequest(url): 9 | ''' 10 | 包装urllib2的请求 11 | ''' 12 | encoding_support = ContentEncodingProcessor 13 | opener = urllib2.build_opener(encoding_support, urllib2.HTTPHandler) 14 | req = urllib2.Request(url) 15 | req.add_header('User-Agent','Mozilla/5.0 (Windows;U;Windows NT 5.1;zh-CN;rv:1.9.2.9)Gecko/20100824Firefox/3.6.9') 16 | return req, opener 17 | 18 | 19 | class ContentEncodingProcessor(urllib2.BaseHandler): 20 | ''' 21 | 支持gzip,defalte,加快加载速度 22 | ref:http://www.pythonclub.org/python-network-application/observer-spider 23 | ''' 24 | 25 | """A handler to add gzip capabilities to urllib2 requests """ 26 | # add headers to requests 27 | def http_request(self, req): 28 | req.add_header("Accept-Encoding", "gzip, deflate") 29 | return req 30 | 31 | # decode 32 | def http_response(self, req, resp): 33 | old_resp = resp 34 | # gzip 35 | if resp.headers.get("content-encoding") == "gzip": 36 | gz = GzipFile( 37 | fileobj=StringIO(resp.read()), 38 | mode="r" 39 | ) 40 | resp = urllib2.addinfourl(gz, old_resp.headers, old_resp.url, old_resp.code) 41 | resp.msg = old_resp.msg 42 | # deflate 43 | if resp.headers.get("content-encoding") == "deflate": 44 | gz = StringIO( deflate(resp.read()) ) 45 | resp = urllib2.addinfourl(gz, old_resp.headers, old_resp.url, old_resp.code) # 'class to add info() and 46 | resp.msg = old_resp.msg 47 | return resp 48 | 49 | # deflate support 50 | import zlib 51 | def deflate(data): # zlib only provides the zlib compress format, not the deflate format; 52 | try: # so on top of all there's this workaround: 53 | return zlib.decompress(data, -zlib.MAX_WBITS) 54 | except zlib.error: 55 | return zlib.decompress(data) 56 | -------------------------------------------------------------------------------- /sphinx/_build/html/genindex.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | Index — pylinktester 1 documentation 14 | 15 | 16 | 17 | 18 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 42 | 43 |
44 |
45 |
46 |
47 | 48 | 49 |

Index

50 | 51 |
52 | 53 |
54 | 55 | 56 |
57 |
58 |
59 |
60 |
61 | 62 | 63 | 64 | 76 | 77 |
78 |
79 |
80 |
81 | 90 | 94 | 95 | -------------------------------------------------------------------------------- /sphinx/_build/html/search.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | Search — pylinktester 1 documentation 12 | 13 | 14 | 15 | 16 | 25 | 26 | 27 | 28 | 29 | 30 | 33 | 34 | 35 | 36 | 37 | 46 | 47 |
48 |
49 |
50 |
51 | 52 |

Search

53 |
54 | 55 |

56 | Please activate JavaScript to enable the search 57 | functionality. 58 |

59 |
60 |

61 | From here you can search these documents. Enter your search 62 | words into the box below and click "search". Note that the search 63 | function will automatically search for all of the words. Pages 64 | containing fewer words won't appear in the result list. 65 |

66 |
67 | 68 | 69 | 70 |
71 | 72 |
73 | 74 |
75 | 76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 |
85 | 94 | 98 | 99 | -------------------------------------------------------------------------------- /sphinx/_build/html/_static/pygments.css: -------------------------------------------------------------------------------- 1 | .highlight .hll { background-color: #ffffcc } 2 | .highlight { background: #eeffcc; } 3 | .highlight .c { color: #408090; font-style: italic } /* Comment */ 4 | .highlight .err { border: 1px solid #FF0000 } /* Error */ 5 | .highlight .k { color: #007020; font-weight: bold } /* Keyword */ 6 | .highlight .o { color: #666666 } /* Operator */ 7 | .highlight .cm { color: #408090; font-style: italic } /* Comment.Multiline */ 8 | .highlight .cp { color: #007020 } /* Comment.Preproc */ 9 | .highlight .c1 { color: #408090; font-style: italic } /* Comment.Single */ 10 | .highlight .cs { color: #408090; background-color: #fff0f0 } /* Comment.Special */ 11 | .highlight .gd { color: #A00000 } /* Generic.Deleted */ 12 | .highlight .ge { font-style: italic } /* Generic.Emph */ 13 | .highlight .gr { color: #FF0000 } /* Generic.Error */ 14 | .highlight .gh { color: #000080; font-weight: bold } /* Generic.Heading */ 15 | .highlight .gi { color: #00A000 } /* Generic.Inserted */ 16 | .highlight .go { color: #333333 } /* Generic.Output */ 17 | .highlight .gp { color: #c65d09; font-weight: bold } /* Generic.Prompt */ 18 | .highlight .gs { font-weight: bold } /* Generic.Strong */ 19 | .highlight .gu { color: #800080; font-weight: bold } /* Generic.Subheading */ 20 | .highlight .gt { color: #0044DD } /* Generic.Traceback */ 21 | .highlight .kc { color: #007020; font-weight: bold } /* Keyword.Constant */ 22 | .highlight .kd { color: #007020; font-weight: bold } /* Keyword.Declaration */ 23 | .highlight .kn { color: #007020; font-weight: bold } /* Keyword.Namespace */ 24 | .highlight .kp { color: #007020 } /* Keyword.Pseudo */ 25 | .highlight .kr { color: #007020; font-weight: bold } /* Keyword.Reserved */ 26 | .highlight .kt { color: #902000 } /* Keyword.Type */ 27 | .highlight .m { color: #208050 } /* Literal.Number */ 28 | .highlight .s { color: #4070a0 } /* Literal.String */ 29 | .highlight .na { color: #4070a0 } /* Name.Attribute */ 30 | .highlight .nb { color: #007020 } /* Name.Builtin */ 31 | .highlight .nc { color: #0e84b5; font-weight: bold } /* Name.Class */ 32 | .highlight .no { color: #60add5 } /* Name.Constant */ 33 | .highlight .nd { color: #555555; font-weight: bold } /* Name.Decorator */ 34 | .highlight .ni { color: #d55537; font-weight: bold } /* Name.Entity */ 35 | .highlight .ne { color: #007020 } /* Name.Exception */ 36 | .highlight .nf { color: #06287e } /* Name.Function */ 37 | .highlight .nl { color: #002070; font-weight: bold } /* Name.Label */ 38 | .highlight .nn { color: #0e84b5; font-weight: bold } /* Name.Namespace */ 39 | .highlight .nt { color: #062873; font-weight: bold } /* Name.Tag */ 40 | .highlight .nv { color: #bb60d5 } /* Name.Variable */ 41 | .highlight .ow { color: #007020; font-weight: bold } /* Operator.Word */ 42 | .highlight .w { color: #bbbbbb } /* Text.Whitespace */ 43 | .highlight .mf { color: #208050 } /* Literal.Number.Float */ 44 | .highlight .mh { color: #208050 } /* Literal.Number.Hex */ 45 | .highlight .mi { color: #208050 } /* Literal.Number.Integer */ 46 | .highlight .mo { color: #208050 } /* Literal.Number.Oct */ 47 | .highlight .sb { color: #4070a0 } /* Literal.String.Backtick */ 48 | .highlight .sc { color: #4070a0 } /* Literal.String.Char */ 49 | .highlight .sd { color: #4070a0; font-style: italic } /* Literal.String.Doc */ 50 | .highlight .s2 { color: #4070a0 } /* Literal.String.Double */ 51 | .highlight .se { color: #4070a0; font-weight: bold } /* Literal.String.Escape */ 52 | .highlight .sh { color: #4070a0 } /* Literal.String.Heredoc */ 53 | .highlight .si { color: #70a0d0; font-style: italic } /* Literal.String.Interpol */ 54 | .highlight .sx { color: #c65d09 } /* Literal.String.Other */ 55 | .highlight .sr { color: #235388 } /* Literal.String.Regex */ 56 | .highlight .s1 { color: #4070a0 } /* Literal.String.Single */ 57 | .highlight .ss { color: #517918 } /* Literal.String.Symbol */ 58 | .highlight .bp { color: #007020 } /* Name.Builtin.Pseudo */ 59 | .highlight .vc { color: #bb60d5 } /* Name.Variable.Class */ 60 | .highlight .vg { color: #bb60d5 } /* Name.Variable.Global */ 61 | .highlight .vi { color: #bb60d5 } /* Name.Variable.Instance */ 62 | .highlight .il { color: #208050 } /* Literal.Number.Integer.Long */ -------------------------------------------------------------------------------- /sphinx/_build/html/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | Welcome to pylinktester’s documentation! — pylinktester 1 documentation 12 | 13 | 14 | 15 | 16 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 40 | 41 |
42 |
43 |
44 |
45 | 46 |
47 |

Welcome to pylinktester’s documentation!

48 |

Contents:

49 |
50 |
    51 |
52 |
53 |
54 |
55 |

Indices and tables

56 | 61 |
62 | 63 | 64 |
65 |
66 |
67 |
68 |
69 |

Table Of Contents

70 | 76 | 77 |

This Page

78 | 82 | 94 | 95 |
96 |
97 |
98 |
99 | 108 | 112 | 113 | -------------------------------------------------------------------------------- /sphinx/_build/html/_static/default.css: -------------------------------------------------------------------------------- 1 | /* 2 | * default.css_t 3 | * ~~~~~~~~~~~~~ 4 | * 5 | * Sphinx stylesheet -- default theme. 6 | * 7 | * :copyright: Copyright 2007-2011 by the Sphinx team, see AUTHORS. 8 | * :license: BSD, see LICENSE for details. 9 | * 10 | */ 11 | 12 | @import url("basic.css"); 13 | 14 | /* -- page layout ----------------------------------------------------------- */ 15 | 16 | body { 17 | font-family: sans-serif; 18 | font-size: 100%; 19 | background-color: #11303d; 20 | color: #000; 21 | margin: 0; 22 | padding: 0; 23 | } 24 | 25 | div.document { 26 | background-color: #1c4e63; 27 | } 28 | 29 | div.documentwrapper { 30 | float: left; 31 | width: 100%; 32 | } 33 | 34 | div.bodywrapper { 35 | margin: 0 0 0 230px; 36 | } 37 | 38 | div.body { 39 | background-color: #ffffff; 40 | color: #000000; 41 | padding: 0 20px 30px 20px; 42 | } 43 | 44 | div.footer { 45 | color: #ffffff; 46 | width: 100%; 47 | padding: 9px 0 9px 0; 48 | text-align: center; 49 | font-size: 75%; 50 | } 51 | 52 | div.footer a { 53 | color: #ffffff; 54 | text-decoration: underline; 55 | } 56 | 57 | div.related { 58 | background-color: #133f52; 59 | line-height: 30px; 60 | color: #ffffff; 61 | } 62 | 63 | div.related a { 64 | color: #ffffff; 65 | } 66 | 67 | div.sphinxsidebar { 68 | } 69 | 70 | div.sphinxsidebar h3 { 71 | font-family: 'Trebuchet MS', sans-serif; 72 | color: #ffffff; 73 | font-size: 1.4em; 74 | font-weight: normal; 75 | margin: 0; 76 | padding: 0; 77 | } 78 | 79 | div.sphinxsidebar h3 a { 80 | color: #ffffff; 81 | } 82 | 83 | div.sphinxsidebar h4 { 84 | font-family: 'Trebuchet MS', sans-serif; 85 | color: #ffffff; 86 | font-size: 1.3em; 87 | font-weight: normal; 88 | margin: 5px 0 0 0; 89 | padding: 0; 90 | } 91 | 92 | div.sphinxsidebar p { 93 | color: #ffffff; 94 | } 95 | 96 | div.sphinxsidebar p.topless { 97 | margin: 5px 10px 10px 10px; 98 | } 99 | 100 | div.sphinxsidebar ul { 101 | margin: 10px; 102 | padding: 0; 103 | color: #ffffff; 104 | } 105 | 106 | div.sphinxsidebar a { 107 | color: #98dbcc; 108 | } 109 | 110 | div.sphinxsidebar input { 111 | border: 1px solid #98dbcc; 112 | font-family: sans-serif; 113 | font-size: 1em; 114 | } 115 | 116 | 117 | 118 | /* -- hyperlink styles ------------------------------------------------------ */ 119 | 120 | a { 121 | color: #355f7c; 122 | text-decoration: none; 123 | } 124 | 125 | a:visited { 126 | color: #355f7c; 127 | text-decoration: none; 128 | } 129 | 130 | a:hover { 131 | text-decoration: underline; 132 | } 133 | 134 | 135 | 136 | /* -- body styles ----------------------------------------------------------- */ 137 | 138 | div.body h1, 139 | div.body h2, 140 | div.body h3, 141 | div.body h4, 142 | div.body h5, 143 | div.body h6 { 144 | font-family: 'Trebuchet MS', sans-serif; 145 | background-color: #f2f2f2; 146 | font-weight: normal; 147 | color: #20435c; 148 | border-bottom: 1px solid #ccc; 149 | margin: 20px -20px 10px -20px; 150 | padding: 3px 0 3px 10px; 151 | } 152 | 153 | div.body h1 { margin-top: 0; font-size: 200%; } 154 | div.body h2 { font-size: 160%; } 155 | div.body h3 { font-size: 140%; } 156 | div.body h4 { font-size: 120%; } 157 | div.body h5 { font-size: 110%; } 158 | div.body h6 { font-size: 100%; } 159 | 160 | a.headerlink { 161 | color: #c60f0f; 162 | font-size: 0.8em; 163 | padding: 0 4px 0 4px; 164 | text-decoration: none; 165 | } 166 | 167 | a.headerlink:hover { 168 | background-color: #c60f0f; 169 | color: white; 170 | } 171 | 172 | div.body p, div.body dd, div.body li { 173 | text-align: justify; 174 | line-height: 130%; 175 | } 176 | 177 | div.admonition p.admonition-title + p { 178 | display: inline; 179 | } 180 | 181 | div.admonition p { 182 | margin-bottom: 5px; 183 | } 184 | 185 | div.admonition pre { 186 | margin-bottom: 5px; 187 | } 188 | 189 | div.admonition ul, div.admonition ol { 190 | margin-bottom: 5px; 191 | } 192 | 193 | div.note { 194 | background-color: #eee; 195 | border: 1px solid #ccc; 196 | } 197 | 198 | div.seealso { 199 | background-color: #ffc; 200 | border: 1px solid #ff6; 201 | } 202 | 203 | div.topic { 204 | background-color: #eee; 205 | } 206 | 207 | div.warning { 208 | background-color: #ffe4e4; 209 | border: 1px solid #f66; 210 | } 211 | 212 | p.admonition-title { 213 | display: inline; 214 | } 215 | 216 | p.admonition-title:after { 217 | content: ":"; 218 | } 219 | 220 | pre { 221 | padding: 5px; 222 | background-color: #eeffcc; 223 | color: #333333; 224 | line-height: 120%; 225 | border: 1px solid #ac9; 226 | border-left: none; 227 | border-right: none; 228 | } 229 | 230 | tt { 231 | background-color: #ecf0f3; 232 | padding: 0 1px 0 1px; 233 | font-size: 0.95em; 234 | } 235 | 236 | th { 237 | background-color: #ede; 238 | } 239 | 240 | .warning tt { 241 | background: #efc2c2; 242 | } 243 | 244 | .note tt { 245 | background: #d6d6d6; 246 | } 247 | 248 | .viewcode-back { 249 | font-family: sans-serif; 250 | } 251 | 252 | div.viewcode-block:target { 253 | background-color: #f4debf; 254 | border-top: 1px solid #ac9; 255 | border-bottom: 1px solid #ac9; 256 | } -------------------------------------------------------------------------------- /sphinx/_build/html/_static/sidebar.js: -------------------------------------------------------------------------------- 1 | /* 2 | * sidebar.js 3 | * ~~~~~~~~~~ 4 | * 5 | * This script makes the Sphinx sidebar collapsible. 6 | * 7 | * .sphinxsidebar contains .sphinxsidebarwrapper. This script adds 8 | * in .sphixsidebar, after .sphinxsidebarwrapper, the #sidebarbutton 9 | * used to collapse and expand the sidebar. 10 | * 11 | * When the sidebar is collapsed the .sphinxsidebarwrapper is hidden 12 | * and the width of the sidebar and the margin-left of the document 13 | * are decreased. When the sidebar is expanded the opposite happens. 14 | * This script saves a per-browser/per-session cookie used to 15 | * remember the position of the sidebar among the pages. 16 | * Once the browser is closed the cookie is deleted and the position 17 | * reset to the default (expanded). 18 | * 19 | * :copyright: Copyright 2007-2011 by the Sphinx team, see AUTHORS. 20 | * :license: BSD, see LICENSE for details. 21 | * 22 | */ 23 | 24 | $(function() { 25 | // global elements used by the functions. 26 | // the 'sidebarbutton' element is defined as global after its 27 | // creation, in the add_sidebar_button function 28 | var bodywrapper = $('.bodywrapper'); 29 | var sidebar = $('.sphinxsidebar'); 30 | var sidebarwrapper = $('.sphinxsidebarwrapper'); 31 | 32 | // for some reason, the document has no sidebar; do not run into errors 33 | if (!sidebar.length) return; 34 | 35 | // original margin-left of the bodywrapper and width of the sidebar 36 | // with the sidebar expanded 37 | var bw_margin_expanded = bodywrapper.css('margin-left'); 38 | var ssb_width_expanded = sidebar.width(); 39 | 40 | // margin-left of the bodywrapper and width of the sidebar 41 | // with the sidebar collapsed 42 | var bw_margin_collapsed = '.8em'; 43 | var ssb_width_collapsed = '.8em'; 44 | 45 | // colors used by the current theme 46 | var dark_color = $('.related').css('background-color'); 47 | var light_color = $('.document').css('background-color'); 48 | 49 | function sidebar_is_collapsed() { 50 | return sidebarwrapper.is(':not(:visible)'); 51 | } 52 | 53 | function toggle_sidebar() { 54 | if (sidebar_is_collapsed()) 55 | expand_sidebar(); 56 | else 57 | collapse_sidebar(); 58 | } 59 | 60 | function collapse_sidebar() { 61 | sidebarwrapper.hide(); 62 | sidebar.css('width', ssb_width_collapsed); 63 | bodywrapper.css('margin-left', bw_margin_collapsed); 64 | sidebarbutton.css({ 65 | 'margin-left': '0', 66 | 'height': bodywrapper.height() 67 | }); 68 | sidebarbutton.find('span').text('»'); 69 | sidebarbutton.attr('title', _('Expand sidebar')); 70 | document.cookie = 'sidebar=collapsed'; 71 | } 72 | 73 | function expand_sidebar() { 74 | bodywrapper.css('margin-left', bw_margin_expanded); 75 | sidebar.css('width', ssb_width_expanded); 76 | sidebarwrapper.show(); 77 | sidebarbutton.css({ 78 | 'margin-left': ssb_width_expanded-12, 79 | 'height': bodywrapper.height() 80 | }); 81 | sidebarbutton.find('span').text('«'); 82 | sidebarbutton.attr('title', _('Collapse sidebar')); 83 | document.cookie = 'sidebar=expanded'; 84 | } 85 | 86 | function add_sidebar_button() { 87 | sidebarwrapper.css({ 88 | 'float': 'left', 89 | 'margin-right': '0', 90 | 'width': ssb_width_expanded - 28 91 | }); 92 | // create the button 93 | sidebar.append( 94 | '
«
' 95 | ); 96 | var sidebarbutton = $('#sidebarbutton'); 97 | light_color = sidebarbutton.css('background-color'); 98 | // find the height of the viewport to center the '<<' in the page 99 | var viewport_height; 100 | if (window.innerHeight) 101 | viewport_height = window.innerHeight; 102 | else 103 | viewport_height = $(window).height(); 104 | sidebarbutton.find('span').css({ 105 | 'display': 'block', 106 | 'margin-top': (viewport_height - sidebar.position().top - 20) / 2 107 | }); 108 | 109 | sidebarbutton.click(toggle_sidebar); 110 | sidebarbutton.attr('title', _('Collapse sidebar')); 111 | sidebarbutton.css({ 112 | 'color': '#FFFFFF', 113 | 'border-left': '1px solid ' + dark_color, 114 | 'font-size': '1.2em', 115 | 'cursor': 'pointer', 116 | 'height': bodywrapper.height(), 117 | 'padding-top': '1px', 118 | 'margin-left': ssb_width_expanded - 12 119 | }); 120 | 121 | sidebarbutton.hover( 122 | function () { 123 | $(this).css('background-color', dark_color); 124 | }, 125 | function () { 126 | $(this).css('background-color', light_color); 127 | } 128 | ); 129 | } 130 | 131 | function set_position_from_cookie() { 132 | if (!document.cookie) 133 | return; 134 | var items = document.cookie.split(';'); 135 | for(var k=0; k` where ^ is one of 21 | echo. html to make standalone HTML files 22 | echo. dirhtml to make HTML files named index.html in directories 23 | echo. singlehtml to make a single large HTML file 24 | echo. pickle to make pickle files 25 | echo. json to make JSON files 26 | echo. htmlhelp to make HTML files and a HTML help project 27 | echo. qthelp to make HTML files and a qthelp project 28 | echo. devhelp to make HTML files and a Devhelp project 29 | echo. epub to make an epub 30 | echo. latex to make LaTeX files, you can set PAPER=a4 or PAPER=letter 31 | echo. text to make text files 32 | echo. man to make manual pages 33 | echo. texinfo to make Texinfo files 34 | echo. gettext to make PO message catalogs 35 | echo. changes to make an overview over all changed/added/deprecated items 36 | echo. linkcheck to check all external links for integrity 37 | echo. doctest to run all doctests embedded in the documentation if enabled 38 | goto end 39 | ) 40 | 41 | if "%1" == "clean" ( 42 | for /d %%i in (%BUILDDIR%\*) do rmdir /q /s %%i 43 | del /q /s %BUILDDIR%\* 44 | goto end 45 | ) 46 | 47 | if "%1" == "html" ( 48 | %SPHINXBUILD% -b html %ALLSPHINXOPTS% %BUILDDIR%/html 49 | if errorlevel 1 exit /b 1 50 | echo. 51 | echo.Build finished. The HTML pages are in %BUILDDIR%/html. 52 | goto end 53 | ) 54 | 55 | if "%1" == "dirhtml" ( 56 | %SPHINXBUILD% -b dirhtml %ALLSPHINXOPTS% %BUILDDIR%/dirhtml 57 | if errorlevel 1 exit /b 1 58 | echo. 59 | echo.Build finished. The HTML pages are in %BUILDDIR%/dirhtml. 60 | goto end 61 | ) 62 | 63 | if "%1" == "singlehtml" ( 64 | %SPHINXBUILD% -b singlehtml %ALLSPHINXOPTS% %BUILDDIR%/singlehtml 65 | if errorlevel 1 exit /b 1 66 | echo. 67 | echo.Build finished. The HTML pages are in %BUILDDIR%/singlehtml. 68 | goto end 69 | ) 70 | 71 | if "%1" == "pickle" ( 72 | %SPHINXBUILD% -b pickle %ALLSPHINXOPTS% %BUILDDIR%/pickle 73 | if errorlevel 1 exit /b 1 74 | echo. 75 | echo.Build finished; now you can process the pickle files. 76 | goto end 77 | ) 78 | 79 | if "%1" == "json" ( 80 | %SPHINXBUILD% -b json %ALLSPHINXOPTS% %BUILDDIR%/json 81 | if errorlevel 1 exit /b 1 82 | echo. 83 | echo.Build finished; now you can process the JSON files. 84 | goto end 85 | ) 86 | 87 | if "%1" == "htmlhelp" ( 88 | %SPHINXBUILD% -b htmlhelp %ALLSPHINXOPTS% %BUILDDIR%/htmlhelp 89 | if errorlevel 1 exit /b 1 90 | echo. 91 | echo.Build finished; now you can run HTML Help Workshop with the ^ 92 | .hhp project file in %BUILDDIR%/htmlhelp. 93 | goto end 94 | ) 95 | 96 | if "%1" == "qthelp" ( 97 | %SPHINXBUILD% -b qthelp %ALLSPHINXOPTS% %BUILDDIR%/qthelp 98 | if errorlevel 1 exit /b 1 99 | echo. 100 | echo.Build finished; now you can run "qcollectiongenerator" with the ^ 101 | .qhcp project file in %BUILDDIR%/qthelp, like this: 102 | echo.^> qcollectiongenerator %BUILDDIR%\qthelp\pylinktester.qhcp 103 | echo.To view the help file: 104 | echo.^> assistant -collectionFile %BUILDDIR%\qthelp\pylinktester.ghc 105 | goto end 106 | ) 107 | 108 | if "%1" == "devhelp" ( 109 | %SPHINXBUILD% -b devhelp %ALLSPHINXOPTS% %BUILDDIR%/devhelp 110 | if errorlevel 1 exit /b 1 111 | echo. 112 | echo.Build finished. 113 | goto end 114 | ) 115 | 116 | if "%1" == "epub" ( 117 | %SPHINXBUILD% -b epub %ALLSPHINXOPTS% %BUILDDIR%/epub 118 | if errorlevel 1 exit /b 1 119 | echo. 120 | echo.Build finished. The epub file is in %BUILDDIR%/epub. 121 | goto end 122 | ) 123 | 124 | if "%1" == "latex" ( 125 | %SPHINXBUILD% -b latex %ALLSPHINXOPTS% %BUILDDIR%/latex 126 | if errorlevel 1 exit /b 1 127 | echo. 128 | echo.Build finished; the LaTeX files are in %BUILDDIR%/latex. 129 | goto end 130 | ) 131 | 132 | if "%1" == "text" ( 133 | %SPHINXBUILD% -b text %ALLSPHINXOPTS% %BUILDDIR%/text 134 | if errorlevel 1 exit /b 1 135 | echo. 136 | echo.Build finished. The text files are in %BUILDDIR%/text. 137 | goto end 138 | ) 139 | 140 | if "%1" == "man" ( 141 | %SPHINXBUILD% -b man %ALLSPHINXOPTS% %BUILDDIR%/man 142 | if errorlevel 1 exit /b 1 143 | echo. 144 | echo.Build finished. The manual pages are in %BUILDDIR%/man. 145 | goto end 146 | ) 147 | 148 | if "%1" == "texinfo" ( 149 | %SPHINXBUILD% -b texinfo %ALLSPHINXOPTS% %BUILDDIR%/texinfo 150 | if errorlevel 1 exit /b 1 151 | echo. 152 | echo.Build finished. The Texinfo files are in %BUILDDIR%/texinfo. 153 | goto end 154 | ) 155 | 156 | if "%1" == "gettext" ( 157 | %SPHINXBUILD% -b gettext %I18NSPHINXOPTS% %BUILDDIR%/locale 158 | if errorlevel 1 exit /b 1 159 | echo. 160 | echo.Build finished. The message catalogs are in %BUILDDIR%/locale. 161 | goto end 162 | ) 163 | 164 | if "%1" == "changes" ( 165 | %SPHINXBUILD% -b changes %ALLSPHINXOPTS% %BUILDDIR%/changes 166 | if errorlevel 1 exit /b 1 167 | echo. 168 | echo.The overview file is in %BUILDDIR%/changes. 169 | goto end 170 | ) 171 | 172 | if "%1" == "linkcheck" ( 173 | %SPHINXBUILD% -b linkcheck %ALLSPHINXOPTS% %BUILDDIR%/linkcheck 174 | if errorlevel 1 exit /b 1 175 | echo. 176 | echo.Link check complete; look for any errors in the above output ^ 177 | or in %BUILDDIR%/linkcheck/output.txt. 178 | goto end 179 | ) 180 | 181 | if "%1" == "doctest" ( 182 | %SPHINXBUILD% -b doctest %ALLSPHINXOPTS% %BUILDDIR%/doctest 183 | if errorlevel 1 exit /b 1 184 | echo. 185 | echo.Testing of doctests in the sources finished, look at the ^ 186 | results in %BUILDDIR%/doctest/output.txt. 187 | goto end 188 | ) 189 | 190 | :end 191 | -------------------------------------------------------------------------------- /sphinx/Makefile: -------------------------------------------------------------------------------- 1 | # Makefile for Sphinx documentation 2 | # 3 | 4 | # You can set these variables from the command line. 5 | SPHINXOPTS = 6 | SPHINXBUILD = sphinx-build 7 | PAPER = 8 | BUILDDIR = _build 9 | 10 | # Internal variables. 11 | PAPEROPT_a4 = -D latex_paper_size=a4 12 | PAPEROPT_letter = -D latex_paper_size=letter 13 | ALLSPHINXOPTS = -d $(BUILDDIR)/doctrees $(PAPEROPT_$(PAPER)) $(SPHINXOPTS) . 14 | # the i18n builder cannot share the environment and doctrees with the others 15 | I18NSPHINXOPTS = $(PAPEROPT_$(PAPER)) $(SPHINXOPTS) . 16 | 17 | .PHONY: help clean html dirhtml singlehtml pickle json htmlhelp qthelp devhelp epub latex latexpdf text man changes linkcheck doctest gettext 18 | 19 | help: 20 | @echo "Please use \`make ' where is one of" 21 | @echo " html to make standalone HTML files" 22 | @echo " dirhtml to make HTML files named index.html in directories" 23 | @echo " singlehtml to make a single large HTML file" 24 | @echo " pickle to make pickle files" 25 | @echo " json to make JSON files" 26 | @echo " htmlhelp to make HTML files and a HTML help project" 27 | @echo " qthelp to make HTML files and a qthelp project" 28 | @echo " devhelp to make HTML files and a Devhelp project" 29 | @echo " epub to make an epub" 30 | @echo " latex to make LaTeX files, you can set PAPER=a4 or PAPER=letter" 31 | @echo " latexpdf to make LaTeX files and run them through pdflatex" 32 | @echo " text to make text files" 33 | @echo " man to make manual pages" 34 | @echo " texinfo to make Texinfo files" 35 | @echo " info to make Texinfo files and run them through makeinfo" 36 | @echo " gettext to make PO message catalogs" 37 | @echo " changes to make an overview of all changed/added/deprecated items" 38 | @echo " linkcheck to check all external links for integrity" 39 | @echo " doctest to run all doctests embedded in the documentation (if enabled)" 40 | 41 | clean: 42 | -rm -rf $(BUILDDIR)/* 43 | 44 | html: 45 | $(SPHINXBUILD) -b html $(ALLSPHINXOPTS) $(BUILDDIR)/html 46 | @echo 47 | @echo "Build finished. The HTML pages are in $(BUILDDIR)/html." 48 | 49 | dirhtml: 50 | $(SPHINXBUILD) -b dirhtml $(ALLSPHINXOPTS) $(BUILDDIR)/dirhtml 51 | @echo 52 | @echo "Build finished. The HTML pages are in $(BUILDDIR)/dirhtml." 53 | 54 | singlehtml: 55 | $(SPHINXBUILD) -b singlehtml $(ALLSPHINXOPTS) $(BUILDDIR)/singlehtml 56 | @echo 57 | @echo "Build finished. The HTML page is in $(BUILDDIR)/singlehtml." 58 | 59 | pickle: 60 | $(SPHINXBUILD) -b pickle $(ALLSPHINXOPTS) $(BUILDDIR)/pickle 61 | @echo 62 | @echo "Build finished; now you can process the pickle files." 63 | 64 | json: 65 | $(SPHINXBUILD) -b json $(ALLSPHINXOPTS) $(BUILDDIR)/json 66 | @echo 67 | @echo "Build finished; now you can process the JSON files." 68 | 69 | htmlhelp: 70 | $(SPHINXBUILD) -b htmlhelp $(ALLSPHINXOPTS) $(BUILDDIR)/htmlhelp 71 | @echo 72 | @echo "Build finished; now you can run HTML Help Workshop with the" \ 73 | ".hhp project file in $(BUILDDIR)/htmlhelp." 74 | 75 | qthelp: 76 | $(SPHINXBUILD) -b qthelp $(ALLSPHINXOPTS) $(BUILDDIR)/qthelp 77 | @echo 78 | @echo "Build finished; now you can run "qcollectiongenerator" with the" \ 79 | ".qhcp project file in $(BUILDDIR)/qthelp, like this:" 80 | @echo "# qcollectiongenerator $(BUILDDIR)/qthelp/pylinktester.qhcp" 81 | @echo "To view the help file:" 82 | @echo "# assistant -collectionFile $(BUILDDIR)/qthelp/pylinktester.qhc" 83 | 84 | devhelp: 85 | $(SPHINXBUILD) -b devhelp $(ALLSPHINXOPTS) $(BUILDDIR)/devhelp 86 | @echo 87 | @echo "Build finished." 88 | @echo "To view the help file:" 89 | @echo "# mkdir -p $$HOME/.local/share/devhelp/pylinktester" 90 | @echo "# ln -s $(BUILDDIR)/devhelp $$HOME/.local/share/devhelp/pylinktester" 91 | @echo "# devhelp" 92 | 93 | epub: 94 | $(SPHINXBUILD) -b epub $(ALLSPHINXOPTS) $(BUILDDIR)/epub 95 | @echo 96 | @echo "Build finished. The epub file is in $(BUILDDIR)/epub." 97 | 98 | latex: 99 | $(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex 100 | @echo 101 | @echo "Build finished; the LaTeX files are in $(BUILDDIR)/latex." 102 | @echo "Run \`make' in that directory to run these through (pdf)latex" \ 103 | "(use \`make latexpdf' here to do that automatically)." 104 | 105 | latexpdf: 106 | $(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex 107 | @echo "Running LaTeX files through pdflatex..." 108 | $(MAKE) -C $(BUILDDIR)/latex all-pdf 109 | @echo "pdflatex finished; the PDF files are in $(BUILDDIR)/latex." 110 | 111 | text: 112 | $(SPHINXBUILD) -b text $(ALLSPHINXOPTS) $(BUILDDIR)/text 113 | @echo 114 | @echo "Build finished. The text files are in $(BUILDDIR)/text." 115 | 116 | man: 117 | $(SPHINXBUILD) -b man $(ALLSPHINXOPTS) $(BUILDDIR)/man 118 | @echo 119 | @echo "Build finished. The manual pages are in $(BUILDDIR)/man." 120 | 121 | texinfo: 122 | $(SPHINXBUILD) -b texinfo $(ALLSPHINXOPTS) $(BUILDDIR)/texinfo 123 | @echo 124 | @echo "Build finished. The Texinfo files are in $(BUILDDIR)/texinfo." 125 | @echo "Run \`make' in that directory to run these through makeinfo" \ 126 | "(use \`make info' here to do that automatically)." 127 | 128 | info: 129 | $(SPHINXBUILD) -b texinfo $(ALLSPHINXOPTS) $(BUILDDIR)/texinfo 130 | @echo "Running Texinfo files through makeinfo..." 131 | make -C $(BUILDDIR)/texinfo info 132 | @echo "makeinfo finished; the Info files are in $(BUILDDIR)/texinfo." 133 | 134 | gettext: 135 | $(SPHINXBUILD) -b gettext $(I18NSPHINXOPTS) $(BUILDDIR)/locale 136 | @echo 137 | @echo "Build finished. The message catalogs are in $(BUILDDIR)/locale." 138 | 139 | changes: 140 | $(SPHINXBUILD) -b changes $(ALLSPHINXOPTS) $(BUILDDIR)/changes 141 | @echo 142 | @echo "The overview file is in $(BUILDDIR)/changes." 143 | 144 | linkcheck: 145 | $(SPHINXBUILD) -b linkcheck $(ALLSPHINXOPTS) $(BUILDDIR)/linkcheck 146 | @echo 147 | @echo "Link check complete; look for any errors in the above output " \ 148 | "or in $(BUILDDIR)/linkcheck/output.txt." 149 | 150 | doctest: 151 | $(SPHINXBUILD) -b doctest $(ALLSPHINXOPTS) $(BUILDDIR)/doctest 152 | @echo "Testing of doctests in the sources finished, look at the " \ 153 | "results in $(BUILDDIR)/doctest/output.txt." 154 | -------------------------------------------------------------------------------- /pylinktester/logs/2014-02-08.txt: -------------------------------------------------------------------------------- 1 | 2014-02-08 10:59:44 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=zs_399001&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 2 | 2014-02-08 10:59:44 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=zs_000001&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 3 | 2014-02-08 10:59:44 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=zs_000001&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 4 | 2014-02-08 10:59:45 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=zs_399001&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 5 | 2014-02-08 10:59:49 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=MyStock&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 6 | 2014-02-08 10:59:49 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/?v=2&_smuid=Bjd4xNZEjDLFgIjuQEgkRs 7 | 2014-02-08 10:59:52 HTTP Error 503: Service Temporarily Unavailablehttp://vip.book.sohu.com/c/5/?_smuid=0Km7t64OY7hABHRmgJPBp1 8 | 2014-02-08 10:59:53 HTTP Error 503: Service Temporarily Unavailablehttp://vip.book.sohu.com/m/nav/type.html 9 | 2014-02-08 10:59:53 HTTP Error 503: Service Temporarily Unavailablehttp://vip.book.sohu.com/m/category.php?qianyue=0&mc=82&sc=86&tl=0&bs=0&ld=0&fl=0&vip=0&ord=0 10 | 2014-02-08 10:59:53 HTTP Error 503: Service Temporarily Unavailablehttp://vip.book.sohu.com/m/book/?book_id=130669 11 | 2014-02-08 10:59:53 HTTP Error 404: Not Foundhttp://vip.book.sohu.com/c/4/?_smuid=0Km7t64OY7hABHRmgJPBp1 12 | 2014-02-08 10:59:53 HTTP Error 503: Service Temporarily Unavailablehttp://vip.book.sohu.com/m/top/wap.php?ord=3 13 | 2014-02-08 10:59:53 HTTP Error 503: Service Temporarily Unavailablehttp://vip.book.sohu.com/m/book/?book_id=122819 14 | 2014-02-08 10:59:53 HTTP Error 503: Service Temporarily Unavailablehttp://vip.book.sohu.com/m/book/?book_id=118392 15 | 2014-02-08 10:59:53 HTTP Error 503: Service Temporarily Unavailablehttp://vip.book.sohu.com/m/category.php?qianyue=0&mc=82&sc=86&tl=0&bs=0&ld=0&fl=0&vip=1&ord=0 16 | 2014-02-08 10:59:53 HTTP Error 503: Service Temporarily Unavailablehttp://vip.book.sohu.com/c/10/?_smuid=0Km7t64OY7hABHRmgJPBp1 17 | 2014-02-08 10:59:53 HTTP Error 404: Not Foundhttp://vip.book.sohu.com/c/3/?_smuid=0Km7t64OY7hABHRmgJPBp1 18 | 2014-02-08 10:59:53 HTTP Error 503: Service Temporarily Unavailablehttp://vip.book.sohu.com/c/395/?_smuid=0Km7t64OY7hABHRmgJPBp1 19 | 2014-02-08 10:59:53 HTTP Error 503: Service Temporarily Unavailablehttp://vip.book.sohu.com/m/book/?book_id=128160 20 | 2014-02-08 10:59:53 HTTP Error 404: Not Foundhttp://vip.book.sohu.com/c/7/?_smuid=0Km7t64OY7hABHRmgJPBp1 21 | 2014-02-08 10:59:53 HTTP Error 404: Not Foundhttp://vip.book.sohu.com/c/2/?_smuid=0Km7t64OY7hABHRmgJPBp1 22 | 2014-02-08 10:59:53 HTTP Error 503: Service Temporarily Unavailablehttp://vip.book.sohu.com/c/326/?_smuid=0Km7t64OY7hABHRmgJPBp1 23 | 2014-02-08 10:59:54 HTTP Error 404: Not Foundhttp://vip.book.sohu.com/c/8/?_smuid=0Km7t64OY7hABHRmgJPBp1 24 | 2014-02-08 10:59:55 HTTP Error 404: Not Foundhttp://wap.cmread.com/iread/wml/p/zhb201310.jsp?cm=M6042290 25 | 2014-02-08 10:59:59 HTTP Error 404: Not Foundhttp://vip.book.sohu.com/c/7/?_smuid=0Km7t64OY7hABHRmgJPBp1 26 | 2014-02-08 10:59:59 HTTP Error 404: Not Foundhttp://vip.book.sohu.com/c/326/?_smuid=0Km7t64OY7hABHRmgJPBp1 27 | 2014-02-08 11:00:00 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=cn_300023&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 28 | 2014-02-08 11:00:00 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=cn_000988&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 29 | 2014-02-08 11:00:00 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=cn_600731&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 30 | 2014-02-08 11:00:00 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=Top&type=top_sh_turnover_up&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 31 | 2014-02-08 11:00:00 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=SectorStockTop&code=1050&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 32 | 2014-02-08 11:00:00 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=SectorTop&type=sectorUPTop&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 33 | 2014-02-08 11:00:00 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=SectorStockTop&code=1511&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 34 | 2014-02-08 11:00:00 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=SectorStockTop&code=630&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 35 | 2014-02-08 11:00:00 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=SectorStockTop&code=1490&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 36 | 2014-02-08 11:00:00 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=cn_300219&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 37 | 2014-02-08 11:00:00 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=cn_600640&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 38 | 2014-02-08 11:00:01 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=cn_600390&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 39 | 2014-02-08 11:00:01 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=Top&type=top_sh_changerate_up&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 40 | 2014-02-08 11:00:01 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=cn_600228&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 41 | 2014-02-08 11:00:01 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=Top&type=top_sh_turnoverrate&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 42 | 2014-02-08 11:00:01 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=cn_000829&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 43 | 2014-02-08 11:00:01 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=Top&type=top_sh_volume_up&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 44 | 2014-02-08 11:00:01 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=SectorStockTop&code=810&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 45 | 2014-02-08 11:00:01 HTTP Error 500: Internal Server Errorhttp://s.m.sohu.com/fin_web/jump.do?forward=StockIndex&code=cn_601929&_smuid=Bjd4xNZEjDLFgIjuQEgkRs&v=2 46 | 2014-02-08 11:00:03 HTTP Error 404: Not Foundhttp://www.uc.cn/product/uc_sky_download.shtml 47 | 2014-02-08 11:00:05 HTTP Error 404: Not Foundhttp://reg.uc.cn/ssowww/web/ 48 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | pylinktester 2 | ============ 3 | 4 | 一个python写的多线程网站链接检测器,检测链接是否可达 5 | 6 | ============ 7 | 运行预览: 8 | 9 | 第1层未访问链接出队 "http://lazynight.me" 10 | 11 | 第2层未访问链接出队 "http://lazynight.me/2916.html" 12 | 13 | 第2层未访问链接出队 "http://lazynight.me/2898.html#comments" 14 | 15 | 第2层未访问链接出队 "http://lazynight.me/category/infiltration" 16 | 17 | 第2层未访问链接出队 "http://lazynight.me/2544.html" 18 | 19 | 第2层未访问链接出队 "http://lazynight.me/category/Java" 20 | 21 | 第2层未访问链接出队 "http://lazynight.me/2927.html#comments" 22 | 23 | 第2层未访问链接出队 "http://lazynight.me/2952.html#comments" 24 | 25 | 第2层未访问链接出队 "http://luoo.net" 26 | 27 | 第2层未访问链接出队 "http://lazynight.me/2876.html#comments" 28 | 29 | 第2层未访问链接出队 "http://www.xliebo.com/ " 30 | 31 | 第2层未访问链接出队 "http://lazynight.me/2932.html" 32 | 33 | 第2层未访问链接出队 "http://lazynight.me/category/php" 34 | 35 | 第2层未访问链接出队 "http://lazynight.me/category/JS/" 36 | 37 | 第2层未访问链接出队 "http://lazynight.me/2934.html#comments" 38 | 39 | 第2层未访问链接出队 "http://lazynight.me/2915.html#comments" 40 | 41 | 第2层未访问链接出队 "http://lazynight.me/category/THREE-JS" 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 第2层未访问链接出队 "http://lazynight.me/2939.html" 82 | 83 | 第2层未访问链接出队 "http://lazynight.me/category/discuz" 84 | 85 | 第2层未访问链接出队 "http://lazynight.me/category/mysql" 86 | 87 | 第2层未访问链接出队 "http://lazynight.me/2952.html" 88 | 89 | 剩余链接数量 685 90 | 91 | 92 | 93 | 第2层未访问链接出队 "http://lazynight.me/category/notes" 94 | 95 | 第2层未访问链接出队 "http://www.iyinman.com/ " 96 | 97 | 剩余链接数量 836 98 | 99 | 100 | 101 | 第2层未访问链接出队 "http://lazynight.me/category/injection" 102 | 103 | 剩余链接数量 891 104 | 105 | 106 | 107 | 剩余链接数量 890 108 | 109 | 110 | 111 | 剩余链接数量 889 112 | 113 | 114 | 115 | 剩余链接数量 888 116 | 117 | 118 | 119 | 剩余链接数量 887 120 | 121 | 122 | 123 | 第2层未访问链接出队 "http://jing.fm" 124 | 125 | 剩余链接数量 911 126 | 127 | 128 | 129 | 剩余链接数量 910 130 | 131 | 132 | 133 | 剩余链接数量 909 134 | 135 | 136 | 137 | 剩余链接数量 908 138 | 139 | 140 | 141 | 第2层未访问链接出队 "http://lazynight.me/category/embedded" 142 | 143 | 剩余链接数量 908 144 | 145 | 146 | 147 | 剩余链接数量 907 148 | 149 | 150 | 151 | 剩余链接数量 906 152 | 153 | 154 | 155 | 剩余链接数量 905 156 | 157 | 158 | 159 | 第2层未访问链接出队 "http://lazynight.me/category/exploits" 160 | 161 | 剩余链接数量 931 162 | 163 | 164 | 165 | 剩余链接数量 930 166 | 167 | 168 | 169 | 剩余链接数量 929 170 | 171 | 172 | 173 | 剩余链接数量 928 174 | 175 | 176 | 177 | 第2层未访问链接出队 "http://lazynight.me/2544.html#comments" 178 | 179 | 剩余链接数量 983 180 | 181 | 182 | 183 | 剩余链接数量 982 184 | 185 | 186 | 187 | 剩余链接数量 981 188 | 189 | 190 | 191 | 第2层未访问链接出队 "http://lazynight.me/2925.html#comments" 192 | 193 | 剩余链接数量 1035 194 | 195 | 196 | 197 | 第2层未访问链接出队 "http://lazynight.me/ads" 198 | 199 | 剩余链接数量 1071 200 | 201 | 202 | 203 | 第2层未访问链接出队 "http://lazynight.me/category/typecho" 204 | 205 | 第2层未访问链接出队 "http://lazynight.me/tools/UP.htm" 206 | 207 | 剩余链接数量 1196 208 | 209 | 210 | 211 | 第2层未访问链接出队 "http://lazynight.me/tags" 212 | 213 | 第2层未访问链接出队 "http://lazynight.me/category/ajax" 214 | 215 | 剩余链接数量 1990 216 | 217 | 218 | 219 | 剩余链接数量 1989 220 | 221 | 222 | 223 | 剩余链接数量 1988 224 | 225 | 226 | 227 | 剩余链接数量 1987 228 | 229 | 230 | 231 | 剩余链接数量 1986 232 | 233 | 234 | 235 | 第2层未访问链接出队 "http://lazynight.me/2895.html#comments" 236 | 237 | 剩余链接数量 2033 238 | 239 | 240 | 241 | 剩余链接数量 2032 242 | 243 | 244 | 245 | 剩余链接数量 2031 246 | 247 | 248 | 249 | 剩余链接数量 2030 250 | 251 | 252 | 253 | 第2层未访问链接出队 "http://www.last.fm" 254 | 255 | 剩余链接数量 2032 256 | 257 | 258 | 259 | 第2层未访问链接出队 "http://lazynight.me/2895.html" 260 | 261 | 剩余链接数量 2051 262 | 263 | 264 | 265 | 剩余链接数量 2050 266 | 267 | 268 | 269 | 第2层未访问链接出队 "http://lazynight.me/2935.html" 270 | 271 | 剩余链接数量 2082 272 | 273 | 274 | -------------------------------------------------------------------------------- /sphinx/_build/html/_static/doctools.js: -------------------------------------------------------------------------------- 1 | /* 2 | * doctools.js 3 | * ~~~~~~~~~~~ 4 | * 5 | * Sphinx JavaScript utilities for all documentation. 6 | * 7 | * :copyright: Copyright 2007-2011 by the Sphinx team, see AUTHORS. 8 | * :license: BSD, see LICENSE for details. 9 | * 10 | */ 11 | 12 | /** 13 | * select a different prefix for underscore 14 | */ 15 | $u = _.noConflict(); 16 | 17 | /** 18 | * make the code below compatible with browsers without 19 | * an installed firebug like debugger 20 | if (!window.console || !console.firebug) { 21 | var names = ["log", "debug", "info", "warn", "error", "assert", "dir", 22 | "dirxml", "group", "groupEnd", "time", "timeEnd", "count", "trace", 23 | "profile", "profileEnd"]; 24 | window.console = {}; 25 | for (var i = 0; i < names.length; ++i) 26 | window.console[names[i]] = function() {}; 27 | } 28 | */ 29 | 30 | /** 31 | * small helper function to urldecode strings 32 | */ 33 | jQuery.urldecode = function(x) { 34 | return decodeURIComponent(x).replace(/\+/g, ' '); 35 | } 36 | 37 | /** 38 | * small helper function to urlencode strings 39 | */ 40 | jQuery.urlencode = encodeURIComponent; 41 | 42 | /** 43 | * This function returns the parsed url parameters of the 44 | * current request. Multiple values per key are supported, 45 | * it will always return arrays of strings for the value parts. 46 | */ 47 | jQuery.getQueryParameters = function(s) { 48 | if (typeof s == 'undefined') 49 | s = document.location.search; 50 | var parts = s.substr(s.indexOf('?') + 1).split('&'); 51 | var result = {}; 52 | for (var i = 0; i < parts.length; i++) { 53 | var tmp = parts[i].split('=', 2); 54 | var key = jQuery.urldecode(tmp[0]); 55 | var value = jQuery.urldecode(tmp[1]); 56 | if (key in result) 57 | result[key].push(value); 58 | else 59 | result[key] = [value]; 60 | } 61 | return result; 62 | }; 63 | 64 | /** 65 | * small function to check if an array contains 66 | * a given item. 67 | */ 68 | jQuery.contains = function(arr, item) { 69 | for (var i = 0; i < arr.length; i++) { 70 | if (arr[i] == item) 71 | return true; 72 | } 73 | return false; 74 | }; 75 | 76 | /** 77 | * highlight a given string on a jquery object by wrapping it in 78 | * span elements with the given class name. 79 | */ 80 | jQuery.fn.highlightText = function(text, className) { 81 | function highlight(node) { 82 | if (node.nodeType == 3) { 83 | var val = node.nodeValue; 84 | var pos = val.toLowerCase().indexOf(text); 85 | if (pos >= 0 && !jQuery(node.parentNode).hasClass(className)) { 86 | var span = document.createElement("span"); 87 | span.className = className; 88 | span.appendChild(document.createTextNode(val.substr(pos, text.length))); 89 | node.parentNode.insertBefore(span, node.parentNode.insertBefore( 90 | document.createTextNode(val.substr(pos + text.length)), 91 | node.nextSibling)); 92 | node.nodeValue = val.substr(0, pos); 93 | } 94 | } 95 | else if (!jQuery(node).is("button, select, textarea")) { 96 | jQuery.each(node.childNodes, function() { 97 | highlight(this); 98 | }); 99 | } 100 | } 101 | return this.each(function() { 102 | highlight(this); 103 | }); 104 | }; 105 | 106 | /** 107 | * Small JavaScript module for the documentation. 108 | */ 109 | var Documentation = { 110 | 111 | init : function() { 112 | this.fixFirefoxAnchorBug(); 113 | this.highlightSearchWords(); 114 | this.initIndexTable(); 115 | }, 116 | 117 | /** 118 | * i18n support 119 | */ 120 | TRANSLATIONS : {}, 121 | PLURAL_EXPR : function(n) { return n == 1 ? 0 : 1; }, 122 | LOCALE : 'unknown', 123 | 124 | // gettext and ngettext don't access this so that the functions 125 | // can safely bound to a different name (_ = Documentation.gettext) 126 | gettext : function(string) { 127 | var translated = Documentation.TRANSLATIONS[string]; 128 | if (typeof translated == 'undefined') 129 | return string; 130 | return (typeof translated == 'string') ? translated : translated[0]; 131 | }, 132 | 133 | ngettext : function(singular, plural, n) { 134 | var translated = Documentation.TRANSLATIONS[singular]; 135 | if (typeof translated == 'undefined') 136 | return (n == 1) ? singular : plural; 137 | return translated[Documentation.PLURALEXPR(n)]; 138 | }, 139 | 140 | addTranslations : function(catalog) { 141 | for (var key in catalog.messages) 142 | this.TRANSLATIONS[key] = catalog.messages[key]; 143 | this.PLURAL_EXPR = new Function('n', 'return +(' + catalog.plural_expr + ')'); 144 | this.LOCALE = catalog.locale; 145 | }, 146 | 147 | /** 148 | * add context elements like header anchor links 149 | */ 150 | addContextElements : function() { 151 | $('div[id] > :header:first').each(function() { 152 | $('\u00B6'). 153 | attr('href', '#' + this.id). 154 | attr('title', _('Permalink to this headline')). 155 | appendTo(this); 156 | }); 157 | $('dt[id]').each(function() { 158 | $('\u00B6'). 159 | attr('href', '#' + this.id). 160 | attr('title', _('Permalink to this definition')). 161 | appendTo(this); 162 | }); 163 | }, 164 | 165 | /** 166 | * workaround a firefox stupidity 167 | */ 168 | fixFirefoxAnchorBug : function() { 169 | if (document.location.hash && $.browser.mozilla) 170 | window.setTimeout(function() { 171 | document.location.href += ''; 172 | }, 10); 173 | }, 174 | 175 | /** 176 | * highlight the search words provided in the url in the text 177 | */ 178 | highlightSearchWords : function() { 179 | var params = $.getQueryParameters(); 180 | var terms = (params.highlight) ? params.highlight[0].split(/\s+/) : []; 181 | if (terms.length) { 182 | var body = $('div.body'); 183 | window.setTimeout(function() { 184 | $.each(terms, function() { 185 | body.highlightText(this.toLowerCase(), 'highlighted'); 186 | }); 187 | }, 10); 188 | $('') 190 | .appendTo($('#searchbox')); 191 | } 192 | }, 193 | 194 | /** 195 | * init the domain index toggle buttons 196 | */ 197 | initIndexTable : function() { 198 | var togglers = $('img.toggler').click(function() { 199 | var src = $(this).attr('src'); 200 | var idnum = $(this).attr('id').substr(7); 201 | $('tr.cg-' + idnum).toggle(); 202 | if (src.substr(-9) == 'minus.png') 203 | $(this).attr('src', src.substr(0, src.length-9) + 'plus.png'); 204 | else 205 | $(this).attr('src', src.substr(0, src.length-8) + 'minus.png'); 206 | }).css('display', ''); 207 | if (DOCUMENTATION_OPTIONS.COLLAPSE_INDEX) { 208 | togglers.click(); 209 | } 210 | }, 211 | 212 | /** 213 | * helper function to hide the search marks again 214 | */ 215 | hideSearchWords : function() { 216 | $('#searchbox .highlight-link').fadeOut(300); 217 | $('span.highlighted').removeClass('highlighted'); 218 | }, 219 | 220 | /** 221 | * make the url absolute 222 | */ 223 | makeURL : function(relativeURL) { 224 | return DOCUMENTATION_OPTIONS.URL_ROOT + '/' + relativeURL; 225 | }, 226 | 227 | /** 228 | * get the current relative url 229 | */ 230 | getCurrentURL : function() { 231 | var path = document.location.pathname; 232 | var parts = path.split(/\//); 233 | $.each(DOCUMENTATION_OPTIONS.URL_ROOT.split(/\//), function() { 234 | if (this == '..') 235 | parts.pop(); 236 | }); 237 | var url = parts.join('/'); 238 | return path.substring(url.lastIndexOf('/') + 1, path.length - 1); 239 | } 240 | }; 241 | 242 | // quick alias for translations 243 | _ = Documentation.gettext; 244 | 245 | $(document).ready(function() { 246 | Documentation.init(); 247 | }); 248 | -------------------------------------------------------------------------------- /sphinx/_build/html/_static/underscore.js: -------------------------------------------------------------------------------- 1 | // Underscore.js 0.5.5 2 | // (c) 2009 Jeremy Ashkenas, DocumentCloud Inc. 3 | // Underscore is freely distributable under the terms of the MIT license. 4 | // Portions of Underscore are inspired by or borrowed from Prototype.js, 5 | // Oliver Steele's Functional, and John Resig's Micro-Templating. 6 | // For all details and documentation: 7 | // http://documentcloud.github.com/underscore/ 8 | (function(){var j=this,n=j._,i=function(a){this._wrapped=a},m=typeof StopIteration!=="undefined"?StopIteration:"__break__",b=j._=function(a){return new i(a)};if(typeof exports!=="undefined")exports._=b;var k=Array.prototype.slice,o=Array.prototype.unshift,p=Object.prototype.toString,q=Object.prototype.hasOwnProperty,r=Object.prototype.propertyIsEnumerable;b.VERSION="0.5.5";b.each=function(a,c,d){try{if(a.forEach)a.forEach(c,d);else if(b.isArray(a)||b.isArguments(a))for(var e=0,f=a.length;e=e.computed&&(e={value:f,computed:g})});return e.value};b.min=function(a,c,d){if(!c&&b.isArray(a))return Math.min.apply(Math,a);var e={computed:Infinity};b.each(a,function(f,g,h){g=c?c.call(d,f,g,h):f;gf?1:0}),"value")};b.sortedIndex=function(a,c,d){d=d||b.identity;for(var e=0,f=a.length;e>1;d(a[g])=0})})};b.zip=function(){for(var a=b.toArray(arguments),c=b.max(b.pluck(a,"length")),d=new Array(c),e=0;e0?f-c:c-f)>=0)return e;e[g++]=f}};b.bind=function(a,c){var d=b.rest(arguments,2);return function(){return a.apply(c||j,d.concat(b.toArray(arguments)))}};b.bindAll=function(a){var c=b.rest(arguments);if(c.length==0)c=b.functions(a);b.each(c,function(d){a[d]=b.bind(a[d],a)}); 17 | return a};b.delay=function(a,c){var d=b.rest(arguments,2);return setTimeout(function(){return a.apply(a,d)},c)};b.defer=function(a){return b.delay.apply(b,[a,1].concat(b.rest(arguments)))};b.wrap=function(a,c){return function(){var d=[a].concat(b.toArray(arguments));return c.apply(c,d)}};b.compose=function(){var a=b.toArray(arguments);return function(){for(var c=b.toArray(arguments),d=a.length-1;d>=0;d--)c=[a[d].apply(this,c)];return c[0]}};b.keys=function(a){if(b.isArray(a))return b.range(0,a.length); 18 | var c=[];for(var d in a)q.call(a,d)&&c.push(d);return c};b.values=function(a){return b.map(a,b.identity)};b.functions=function(a){return b.select(b.keys(a),function(c){return b.isFunction(a[c])}).sort()};b.extend=function(a,c){for(var d in c)a[d]=c[d];return a};b.clone=function(a){if(b.isArray(a))return a.slice(0);return b.extend({},a)};b.tap=function(a,c){c(a);return a};b.isEqual=function(a,c){if(a===c)return true;var d=typeof a;if(d!=typeof c)return false;if(a==c)return true;if(!a&&c||a&&!c)return false; 19 | if(a.isEqual)return a.isEqual(c);if(b.isDate(a)&&b.isDate(c))return a.getTime()===c.getTime();if(b.isNaN(a)&&b.isNaN(c))return true;if(b.isRegExp(a)&&b.isRegExp(c))return a.source===c.source&&a.global===c.global&&a.ignoreCase===c.ignoreCase&&a.multiline===c.multiline;if(d!=="object")return false;if(a.length&&a.length!==c.length)return false;d=b.keys(a);var e=b.keys(c);if(d.length!=e.length)return false;for(var f in a)if(!b.isEqual(a[f],c[f]))return false;return true};b.isEmpty=function(a){return b.keys(a).length== 20 | 0};b.isElement=function(a){return!!(a&&a.nodeType==1)};b.isArray=function(a){return!!(a&&a.concat&&a.unshift)};b.isArguments=function(a){return a&&b.isNumber(a.length)&&!b.isArray(a)&&!r.call(a,"length")};b.isFunction=function(a){return!!(a&&a.constructor&&a.call&&a.apply)};b.isString=function(a){return!!(a===""||a&&a.charCodeAt&&a.substr)};b.isNumber=function(a){return p.call(a)==="[object Number]"};b.isDate=function(a){return!!(a&&a.getTimezoneOffset&&a.setUTCFullYear)};b.isRegExp=function(a){return!!(a&& 21 | a.test&&a.exec&&(a.ignoreCase||a.ignoreCase===false))};b.isNaN=function(a){return b.isNumber(a)&&isNaN(a)};b.isNull=function(a){return a===null};b.isUndefined=function(a){return typeof a=="undefined"};b.noConflict=function(){j._=n;return this};b.identity=function(a){return a};b.breakLoop=function(){throw m;};var s=0;b.uniqueId=function(a){var c=s++;return a?a+c:c};b.template=function(a,c){a=new Function("obj","var p=[],print=function(){p.push.apply(p,arguments);};with(obj){p.push('"+a.replace(/[\r\t\n]/g, 22 | " ").replace(/'(?=[^%]*%>)/g,"\t").split("'").join("\\'").split("\t").join("'").replace(/<%=(.+?)%>/g,"',$1,'").split("<%").join("');").split("%>").join("p.push('")+"');}return p.join('');");return c?a(c):a};b.forEach=b.each;b.foldl=b.inject=b.reduce;b.foldr=b.reduceRight;b.filter=b.select;b.every=b.all;b.some=b.any;b.head=b.first;b.tail=b.rest;b.methods=b.functions;var l=function(a,c){return c?b(a).chain():a};b.each(b.functions(b),function(a){var c=b[a];i.prototype[a]=function(){var d=b.toArray(arguments); 23 | o.call(d,this._wrapped);return l(c.apply(b,d),this._chain)}});b.each(["pop","push","reverse","shift","sort","splice","unshift"],function(a){var c=Array.prototype[a];i.prototype[a]=function(){c.apply(this._wrapped,arguments);return l(this._wrapped,this._chain)}});b.each(["concat","join","slice"],function(a){var c=Array.prototype[a];i.prototype[a]=function(){return l(c.apply(this._wrapped,arguments),this._chain)}});i.prototype.chain=function(){this._chain=true;return this};i.prototype.value=function(){return this._wrapped}})(); 24 | -------------------------------------------------------------------------------- /sphinx/conf.py: -------------------------------------------------------------------------------- 1 | # -*- coding: utf-8 -*- 2 | # 3 | # pylinktester documentation build configuration file, created by 4 | # sphinx-quickstart on Tue Nov 19 16:56:57 2013. 5 | # 6 | # This file is execfile()d with the current directory set to its containing dir. 7 | # 8 | # Note that not all possible configuration values are present in this 9 | # autogenerated file. 10 | # 11 | # All configuration values have a default; values that are commented out 12 | # serve to show the default. 13 | 14 | import sys, os 15 | 16 | # If extensions (or modules to document with autodoc) are in another directory, 17 | # add these directories to sys.path here. If the directory is relative to the 18 | # documentation root, use os.path.abspath to make it absolute, like shown here. 19 | #sys.path.insert(0, os.path.abspath('.')) 20 | 21 | # -- General configuration ----------------------------------------------------- 22 | 23 | # If your documentation needs a minimal Sphinx version, state it here. 24 | #needs_sphinx = '1.0' 25 | 26 | # Add any Sphinx extension module names here, as strings. They can be extensions 27 | # coming with Sphinx (named 'sphinx.ext.*') or your custom ones. 28 | extensions = [] 29 | 30 | # Add any paths that contain templates here, relative to this directory. 31 | templates_path = ['_templates'] 32 | 33 | # The suffix of source filenames. 34 | source_suffix = '.rst' 35 | 36 | # The encoding of source files. 37 | #source_encoding = 'utf-8-sig' 38 | 39 | # The master toctree document. 40 | master_doc = 'index' 41 | 42 | # General information about the project. 43 | project = u'pylinktester' 44 | copyright = u'2013, yuzhe' 45 | 46 | # The version info for the project you're documenting, acts as replacement for 47 | # |version| and |release|, also used in various other places throughout the 48 | # built documents. 49 | # 50 | # The short X.Y version. 51 | version = '1' 52 | # The full version, including alpha/beta/rc tags. 53 | release = '1' 54 | 55 | # The language for content autogenerated by Sphinx. Refer to documentation 56 | # for a list of supported languages. 57 | #language = None 58 | 59 | # There are two options for replacing |today|: either, you set today to some 60 | # non-false value, then it is used: 61 | #today = '' 62 | # Else, today_fmt is used as the format for a strftime call. 63 | #today_fmt = '%B %d, %Y' 64 | 65 | # List of patterns, relative to source directory, that match files and 66 | # directories to ignore when looking for source files. 67 | exclude_patterns = ['_build'] 68 | 69 | # The reST default role (used for this markup: `text`) to use for all documents. 70 | #default_role = None 71 | 72 | # If true, '()' will be appended to :func: etc. cross-reference text. 73 | #add_function_parentheses = True 74 | 75 | # If true, the current module name will be prepended to all description 76 | # unit titles (such as .. function::). 77 | #add_module_names = True 78 | 79 | # If true, sectionauthor and moduleauthor directives will be shown in the 80 | # output. They are ignored by default. 81 | #show_authors = False 82 | 83 | # The name of the Pygments (syntax highlighting) style to use. 84 | pygments_style = 'sphinx' 85 | 86 | # A list of ignored prefixes for module index sorting. 87 | #modindex_common_prefix = [] 88 | 89 | 90 | # -- Options for HTML output --------------------------------------------------- 91 | 92 | # The theme to use for HTML and HTML Help pages. See the documentation for 93 | # a list of builtin themes. 94 | html_theme = 'default' 95 | 96 | # Theme options are theme-specific and customize the look and feel of a theme 97 | # further. For a list of options available for each theme, see the 98 | # documentation. 99 | #html_theme_options = {} 100 | 101 | # Add any paths that contain custom themes here, relative to this directory. 102 | #html_theme_path = [] 103 | 104 | # The name for this set of Sphinx documents. If None, it defaults to 105 | # " v documentation". 106 | #html_title = None 107 | 108 | # A shorter title for the navigation bar. Default is the same as html_title. 109 | #html_short_title = None 110 | 111 | # The name of an image file (relative to this directory) to place at the top 112 | # of the sidebar. 113 | #html_logo = None 114 | 115 | # The name of an image file (within the static path) to use as favicon of the 116 | # docs. This file should be a Windows icon file (.ico) being 16x16 or 32x32 117 | # pixels large. 118 | #html_favicon = None 119 | 120 | # Add any paths that contain custom static files (such as style sheets) here, 121 | # relative to this directory. They are copied after the builtin static files, 122 | # so a file named "default.css" will overwrite the builtin "default.css". 123 | html_static_path = ['_static'] 124 | 125 | # If not '', a 'Last updated on:' timestamp is inserted at every page bottom, 126 | # using the given strftime format. 127 | #html_last_updated_fmt = '%b %d, %Y' 128 | 129 | # If true, SmartyPants will be used to convert quotes and dashes to 130 | # typographically correct entities. 131 | #html_use_smartypants = True 132 | 133 | # Custom sidebar templates, maps document names to template names. 134 | #html_sidebars = {} 135 | 136 | # Additional templates that should be rendered to pages, maps page names to 137 | # template names. 138 | #html_additional_pages = {} 139 | 140 | # If false, no module index is generated. 141 | #html_domain_indices = True 142 | 143 | # If false, no index is generated. 144 | #html_use_index = True 145 | 146 | # If true, the index is split into individual pages for each letter. 147 | #html_split_index = False 148 | 149 | # If true, links to the reST sources are added to the pages. 150 | #html_show_sourcelink = True 151 | 152 | # If true, "Created using Sphinx" is shown in the HTML footer. Default is True. 153 | #html_show_sphinx = True 154 | 155 | # If true, "(C) Copyright ..." is shown in the HTML footer. Default is True. 156 | #html_show_copyright = True 157 | 158 | # If true, an OpenSearch description file will be output, and all pages will 159 | # contain a tag referring to it. The value of this option must be the 160 | # base URL from which the finished HTML is served. 161 | #html_use_opensearch = '' 162 | 163 | # This is the file name suffix for HTML files (e.g. ".xhtml"). 164 | #html_file_suffix = None 165 | 166 | # Output file base name for HTML help builder. 167 | htmlhelp_basename = 'pylinktesterdoc' 168 | 169 | 170 | # -- Options for LaTeX output -------------------------------------------------- 171 | 172 | latex_elements = { 173 | # The paper size ('letterpaper' or 'a4paper'). 174 | #'papersize': 'letterpaper', 175 | 176 | # The font size ('10pt', '11pt' or '12pt'). 177 | #'pointsize': '10pt', 178 | 179 | # Additional stuff for the LaTeX preamble. 180 | #'preamble': '', 181 | } 182 | 183 | # Grouping the document tree into LaTeX files. List of tuples 184 | # (source start file, target name, title, author, documentclass [howto/manual]). 185 | latex_documents = [ 186 | ('index', 'pylinktester.tex', u'pylinktester Documentation', 187 | u'yuzhe', 'manual'), 188 | ] 189 | 190 | # The name of an image file (relative to this directory) to place at the top of 191 | # the title page. 192 | #latex_logo = None 193 | 194 | # For "manual" documents, if this is true, then toplevel headings are parts, 195 | # not chapters. 196 | #latex_use_parts = False 197 | 198 | # If true, show page references after internal links. 199 | #latex_show_pagerefs = False 200 | 201 | # If true, show URL addresses after external links. 202 | #latex_show_urls = False 203 | 204 | # Documents to append as an appendix to all manuals. 205 | #latex_appendices = [] 206 | 207 | # If false, no module index is generated. 208 | #latex_domain_indices = True 209 | 210 | 211 | # -- Options for manual page output -------------------------------------------- 212 | 213 | # One entry per manual page. List of tuples 214 | # (source start file, name, description, authors, manual section). 215 | man_pages = [ 216 | ('index', 'pylinktester', u'pylinktester Documentation', 217 | [u'yuzhe'], 1) 218 | ] 219 | 220 | # If true, show URL addresses after external links. 221 | #man_show_urls = False 222 | 223 | 224 | # -- Options for Texinfo output ------------------------------------------------ 225 | 226 | # Grouping the document tree into Texinfo files. List of tuples 227 | # (source start file, target name, title, author, 228 | # dir menu entry, description, category) 229 | texinfo_documents = [ 230 | ('index', 'pylinktester', u'pylinktester Documentation', 231 | u'yuzhe', 'pylinktester', 'One line description of project.', 232 | 'Miscellaneous'), 233 | ] 234 | 235 | # Documents to append as an appendix to all manuals. 236 | #texinfo_appendices = [] 237 | 238 | # If false, no module index is generated. 239 | #texinfo_domain_indices = True 240 | 241 | # How to display URL addresses: 'footnote', 'no', or 'inline'. 242 | #texinfo_show_urls = 'footnote' 243 | -------------------------------------------------------------------------------- /sphinx/_build/html/_static/basic.css: -------------------------------------------------------------------------------- 1 | /* 2 | * basic.css 3 | * ~~~~~~~~~ 4 | * 5 | * Sphinx stylesheet -- basic theme. 6 | * 7 | * :copyright: Copyright 2007-2011 by the Sphinx team, see AUTHORS. 8 | * :license: BSD, see LICENSE for details. 9 | * 10 | */ 11 | 12 | /* -- main layout ----------------------------------------------------------- */ 13 | 14 | div.clearer { 15 | clear: both; 16 | } 17 | 18 | /* -- relbar ---------------------------------------------------------------- */ 19 | 20 | div.related { 21 | width: 100%; 22 | font-size: 90%; 23 | } 24 | 25 | div.related h3 { 26 | display: none; 27 | } 28 | 29 | div.related ul { 30 | margin: 0; 31 | padding: 0 0 0 10px; 32 | list-style: none; 33 | } 34 | 35 | div.related li { 36 | display: inline; 37 | } 38 | 39 | div.related li.right { 40 | float: right; 41 | margin-right: 5px; 42 | } 43 | 44 | /* -- sidebar --------------------------------------------------------------- */ 45 | 46 | div.sphinxsidebarwrapper { 47 | padding: 10px 5px 0 10px; 48 | } 49 | 50 | div.sphinxsidebar { 51 | float: left; 52 | width: 230px; 53 | margin-left: -100%; 54 | font-size: 90%; 55 | } 56 | 57 | div.sphinxsidebar ul { 58 | list-style: none; 59 | } 60 | 61 | div.sphinxsidebar ul ul, 62 | div.sphinxsidebar ul.want-points { 63 | margin-left: 20px; 64 | list-style: square; 65 | } 66 | 67 | div.sphinxsidebar ul ul { 68 | margin-top: 0; 69 | margin-bottom: 0; 70 | } 71 | 72 | div.sphinxsidebar form { 73 | margin-top: 10px; 74 | } 75 | 76 | div.sphinxsidebar input { 77 | border: 1px solid #98dbcc; 78 | font-family: sans-serif; 79 | font-size: 1em; 80 | } 81 | 82 | div.sphinxsidebar #searchbox input[type="text"] { 83 | width: 170px; 84 | } 85 | 86 | div.sphinxsidebar #searchbox input[type="submit"] { 87 | width: 30px; 88 | } 89 | 90 | img { 91 | border: 0; 92 | } 93 | 94 | /* -- search page ----------------------------------------------------------- */ 95 | 96 | ul.search { 97 | margin: 10px 0 0 20px; 98 | padding: 0; 99 | } 100 | 101 | ul.search li { 102 | padding: 5px 0 5px 20px; 103 | background-image: url(file.png); 104 | background-repeat: no-repeat; 105 | background-position: 0 7px; 106 | } 107 | 108 | ul.search li a { 109 | font-weight: bold; 110 | } 111 | 112 | ul.search li div.context { 113 | color: #888; 114 | margin: 2px 0 0 30px; 115 | text-align: left; 116 | } 117 | 118 | ul.keywordmatches li.goodmatch a { 119 | font-weight: bold; 120 | } 121 | 122 | /* -- index page ------------------------------------------------------------ */ 123 | 124 | table.contentstable { 125 | width: 90%; 126 | } 127 | 128 | table.contentstable p.biglink { 129 | line-height: 150%; 130 | } 131 | 132 | a.biglink { 133 | font-size: 1.3em; 134 | } 135 | 136 | span.linkdescr { 137 | font-style: italic; 138 | padding-top: 5px; 139 | font-size: 90%; 140 | } 141 | 142 | /* -- general index --------------------------------------------------------- */ 143 | 144 | table.indextable { 145 | width: 100%; 146 | } 147 | 148 | table.indextable td { 149 | text-align: left; 150 | vertical-align: top; 151 | } 152 | 153 | table.indextable dl, table.indextable dd { 154 | margin-top: 0; 155 | margin-bottom: 0; 156 | } 157 | 158 | table.indextable tr.pcap { 159 | height: 10px; 160 | } 161 | 162 | table.indextable tr.cap { 163 | margin-top: 10px; 164 | background-color: #f2f2f2; 165 | } 166 | 167 | img.toggler { 168 | margin-right: 3px; 169 | margin-top: 3px; 170 | cursor: pointer; 171 | } 172 | 173 | div.modindex-jumpbox { 174 | border-top: 1px solid #ddd; 175 | border-bottom: 1px solid #ddd; 176 | margin: 1em 0 1em 0; 177 | padding: 0.4em; 178 | } 179 | 180 | div.genindex-jumpbox { 181 | border-top: 1px solid #ddd; 182 | border-bottom: 1px solid #ddd; 183 | margin: 1em 0 1em 0; 184 | padding: 0.4em; 185 | } 186 | 187 | /* -- general body styles --------------------------------------------------- */ 188 | 189 | a.headerlink { 190 | visibility: hidden; 191 | } 192 | 193 | h1:hover > a.headerlink, 194 | h2:hover > a.headerlink, 195 | h3:hover > a.headerlink, 196 | h4:hover > a.headerlink, 197 | h5:hover > a.headerlink, 198 | h6:hover > a.headerlink, 199 | dt:hover > a.headerlink { 200 | visibility: visible; 201 | } 202 | 203 | div.body p.caption { 204 | text-align: inherit; 205 | } 206 | 207 | div.body td { 208 | text-align: left; 209 | } 210 | 211 | .field-list ul { 212 | padding-left: 1em; 213 | } 214 | 215 | .first { 216 | margin-top: 0 !important; 217 | } 218 | 219 | p.rubric { 220 | margin-top: 30px; 221 | font-weight: bold; 222 | } 223 | 224 | img.align-left, .figure.align-left, object.align-left { 225 | clear: left; 226 | float: left; 227 | margin-right: 1em; 228 | } 229 | 230 | img.align-right, .figure.align-right, object.align-right { 231 | clear: right; 232 | float: right; 233 | margin-left: 1em; 234 | } 235 | 236 | img.align-center, .figure.align-center, object.align-center { 237 | display: block; 238 | margin-left: auto; 239 | margin-right: auto; 240 | } 241 | 242 | .align-left { 243 | text-align: left; 244 | } 245 | 246 | .align-center { 247 | text-align: center; 248 | } 249 | 250 | .align-right { 251 | text-align: right; 252 | } 253 | 254 | /* -- sidebars -------------------------------------------------------------- */ 255 | 256 | div.sidebar { 257 | margin: 0 0 0.5em 1em; 258 | border: 1px solid #ddb; 259 | padding: 7px 7px 0 7px; 260 | background-color: #ffe; 261 | width: 40%; 262 | float: right; 263 | } 264 | 265 | p.sidebar-title { 266 | font-weight: bold; 267 | } 268 | 269 | /* -- topics ---------------------------------------------------------------- */ 270 | 271 | div.topic { 272 | border: 1px solid #ccc; 273 | padding: 7px 7px 0 7px; 274 | margin: 10px 0 10px 0; 275 | } 276 | 277 | p.topic-title { 278 | font-size: 1.1em; 279 | font-weight: bold; 280 | margin-top: 10px; 281 | } 282 | 283 | /* -- admonitions ----------------------------------------------------------- */ 284 | 285 | div.admonition { 286 | margin-top: 10px; 287 | margin-bottom: 10px; 288 | padding: 7px; 289 | } 290 | 291 | div.admonition dt { 292 | font-weight: bold; 293 | } 294 | 295 | div.admonition dl { 296 | margin-bottom: 0; 297 | } 298 | 299 | p.admonition-title { 300 | margin: 0px 10px 5px 0px; 301 | font-weight: bold; 302 | } 303 | 304 | div.body p.centered { 305 | text-align: center; 306 | margin-top: 25px; 307 | } 308 | 309 | /* -- tables ---------------------------------------------------------------- */ 310 | 311 | table.docutils { 312 | border: 0; 313 | border-collapse: collapse; 314 | } 315 | 316 | table.docutils td, table.docutils th { 317 | padding: 1px 8px 1px 5px; 318 | border-top: 0; 319 | border-left: 0; 320 | border-right: 0; 321 | border-bottom: 1px solid #aaa; 322 | } 323 | 324 | table.field-list td, table.field-list th { 325 | border: 0 !important; 326 | } 327 | 328 | table.footnote td, table.footnote th { 329 | border: 0 !important; 330 | } 331 | 332 | th { 333 | text-align: left; 334 | padding-right: 5px; 335 | } 336 | 337 | table.citation { 338 | border-left: solid 1px gray; 339 | margin-left: 1px; 340 | } 341 | 342 | table.citation td { 343 | border-bottom: none; 344 | } 345 | 346 | /* -- other body styles ----------------------------------------------------- */ 347 | 348 | ol.arabic { 349 | list-style: decimal; 350 | } 351 | 352 | ol.loweralpha { 353 | list-style: lower-alpha; 354 | } 355 | 356 | ol.upperalpha { 357 | list-style: upper-alpha; 358 | } 359 | 360 | ol.lowerroman { 361 | list-style: lower-roman; 362 | } 363 | 364 | ol.upperroman { 365 | list-style: upper-roman; 366 | } 367 | 368 | dl { 369 | margin-bottom: 15px; 370 | } 371 | 372 | dd p { 373 | margin-top: 0px; 374 | } 375 | 376 | dd ul, dd table { 377 | margin-bottom: 10px; 378 | } 379 | 380 | dd { 381 | margin-top: 3px; 382 | margin-bottom: 10px; 383 | margin-left: 30px; 384 | } 385 | 386 | dt:target, .highlighted { 387 | background-color: #fbe54e; 388 | } 389 | 390 | dl.glossary dt { 391 | font-weight: bold; 392 | font-size: 1.1em; 393 | } 394 | 395 | .field-list ul { 396 | margin: 0; 397 | padding-left: 1em; 398 | } 399 | 400 | .field-list p { 401 | margin: 0; 402 | } 403 | 404 | .refcount { 405 | color: #060; 406 | } 407 | 408 | .optional { 409 | font-size: 1.3em; 410 | } 411 | 412 | .versionmodified { 413 | font-style: italic; 414 | } 415 | 416 | .system-message { 417 | background-color: #fda; 418 | padding: 5px; 419 | border: 3px solid red; 420 | } 421 | 422 | .footnote:target { 423 | background-color: #ffa; 424 | } 425 | 426 | .line-block { 427 | display: block; 428 | margin-top: 1em; 429 | margin-bottom: 1em; 430 | } 431 | 432 | .line-block .line-block { 433 | margin-top: 0; 434 | margin-bottom: 0; 435 | margin-left: 1.5em; 436 | } 437 | 438 | .guilabel, .menuselection { 439 | font-family: sans-serif; 440 | } 441 | 442 | .accelerator { 443 | text-decoration: underline; 444 | } 445 | 446 | .classifier { 447 | font-style: oblique; 448 | } 449 | 450 | abbr, acronym { 451 | border-bottom: dotted 1px; 452 | cursor: help; 453 | } 454 | 455 | /* -- code displays --------------------------------------------------------- */ 456 | 457 | pre { 458 | overflow: auto; 459 | overflow-y: hidden; /* fixes display issues on Chrome browsers */ 460 | } 461 | 462 | td.linenos pre { 463 | padding: 5px 0px; 464 | border: 0; 465 | background-color: transparent; 466 | color: #aaa; 467 | } 468 | 469 | table.highlighttable { 470 | margin-left: 0.5em; 471 | } 472 | 473 | table.highlighttable td { 474 | padding: 0 0.5em 0 0.5em; 475 | } 476 | 477 | tt.descname { 478 | background-color: transparent; 479 | font-weight: bold; 480 | font-size: 1.2em; 481 | } 482 | 483 | tt.descclassname { 484 | background-color: transparent; 485 | } 486 | 487 | tt.xref, a tt { 488 | background-color: transparent; 489 | font-weight: bold; 490 | } 491 | 492 | h1 tt, h2 tt, h3 tt, h4 tt, h5 tt, h6 tt { 493 | background-color: transparent; 494 | } 495 | 496 | .viewcode-link { 497 | float: right; 498 | } 499 | 500 | .viewcode-back { 501 | float: right; 502 | font-family: sans-serif; 503 | } 504 | 505 | div.viewcode-block:target { 506 | margin: -1px -10px; 507 | padding: 0 10px; 508 | } 509 | 510 | /* -- math display ---------------------------------------------------------- */ 511 | 512 | img.math { 513 | vertical-align: middle; 514 | } 515 | 516 | div.body div.math p { 517 | text-align: center; 518 | } 519 | 520 | span.eqno { 521 | float: right; 522 | } 523 | 524 | /* -- printout stylesheet --------------------------------------------------- */ 525 | 526 | @media print { 527 | div.document, 528 | div.documentwrapper, 529 | div.bodywrapper { 530 | margin: 0 !important; 531 | width: 100%; 532 | } 533 | 534 | div.sphinxsidebar, 535 | div.related, 536 | div.footer, 537 | #top-link { 538 | display: none; 539 | } 540 | } -------------------------------------------------------------------------------- /sphinx/_build/html/_static/searchtools.js: -------------------------------------------------------------------------------- 1 | /* 2 | * searchtools.js_t 3 | * ~~~~~~~~~~~~~~~~ 4 | * 5 | * Sphinx JavaScript utilties for the full-text search. 6 | * 7 | * :copyright: Copyright 2007-2011 by the Sphinx team, see AUTHORS. 8 | * :license: BSD, see LICENSE for details. 9 | * 10 | */ 11 | 12 | /** 13 | * helper function to return a node containing the 14 | * search summary for a given text. keywords is a list 15 | * of stemmed words, hlwords is the list of normal, unstemmed 16 | * words. the first one is used to find the occurance, the 17 | * latter for highlighting it. 18 | */ 19 | 20 | jQuery.makeSearchSummary = function(text, keywords, hlwords) { 21 | var textLower = text.toLowerCase(); 22 | var start = 0; 23 | $.each(keywords, function() { 24 | var i = textLower.indexOf(this.toLowerCase()); 25 | if (i > -1) 26 | start = i; 27 | }); 28 | start = Math.max(start - 120, 0); 29 | var excerpt = ((start > 0) ? '...' : '') + 30 | $.trim(text.substr(start, 240)) + 31 | ((start + 240 - text.length) ? '...' : ''); 32 | var rv = $('
').text(excerpt); 33 | $.each(hlwords, function() { 34 | rv = rv.highlightText(this, 'highlighted'); 35 | }); 36 | return rv; 37 | } 38 | 39 | 40 | /** 41 | * Porter Stemmer 42 | */ 43 | var Stemmer = function() { 44 | 45 | var step2list = { 46 | ational: 'ate', 47 | tional: 'tion', 48 | enci: 'ence', 49 | anci: 'ance', 50 | izer: 'ize', 51 | bli: 'ble', 52 | alli: 'al', 53 | entli: 'ent', 54 | eli: 'e', 55 | ousli: 'ous', 56 | ization: 'ize', 57 | ation: 'ate', 58 | ator: 'ate', 59 | alism: 'al', 60 | iveness: 'ive', 61 | fulness: 'ful', 62 | ousness: 'ous', 63 | aliti: 'al', 64 | iviti: 'ive', 65 | biliti: 'ble', 66 | logi: 'log' 67 | }; 68 | 69 | var step3list = { 70 | icate: 'ic', 71 | ative: '', 72 | alize: 'al', 73 | iciti: 'ic', 74 | ical: 'ic', 75 | ful: '', 76 | ness: '' 77 | }; 78 | 79 | var c = "[^aeiou]"; // consonant 80 | var v = "[aeiouy]"; // vowel 81 | var C = c + "[^aeiouy]*"; // consonant sequence 82 | var V = v + "[aeiou]*"; // vowel sequence 83 | 84 | var mgr0 = "^(" + C + ")?" + V + C; // [C]VC... is m>0 85 | var meq1 = "^(" + C + ")?" + V + C + "(" + V + ")?$"; // [C]VC[V] is m=1 86 | var mgr1 = "^(" + C + ")?" + V + C + V + C; // [C]VCVC... is m>1 87 | var s_v = "^(" + C + ")?" + v; // vowel in stem 88 | 89 | this.stemWord = function (w) { 90 | var stem; 91 | var suffix; 92 | var firstch; 93 | var origword = w; 94 | 95 | if (w.length < 3) 96 | return w; 97 | 98 | var re; 99 | var re2; 100 | var re3; 101 | var re4; 102 | 103 | firstch = w.substr(0,1); 104 | if (firstch == "y") 105 | w = firstch.toUpperCase() + w.substr(1); 106 | 107 | // Step 1a 108 | re = /^(.+?)(ss|i)es$/; 109 | re2 = /^(.+?)([^s])s$/; 110 | 111 | if (re.test(w)) 112 | w = w.replace(re,"$1$2"); 113 | else if (re2.test(w)) 114 | w = w.replace(re2,"$1$2"); 115 | 116 | // Step 1b 117 | re = /^(.+?)eed$/; 118 | re2 = /^(.+?)(ed|ing)$/; 119 | if (re.test(w)) { 120 | var fp = re.exec(w); 121 | re = new RegExp(mgr0); 122 | if (re.test(fp[1])) { 123 | re = /.$/; 124 | w = w.replace(re,""); 125 | } 126 | } 127 | else if (re2.test(w)) { 128 | var fp = re2.exec(w); 129 | stem = fp[1]; 130 | re2 = new RegExp(s_v); 131 | if (re2.test(stem)) { 132 | w = stem; 133 | re2 = /(at|bl|iz)$/; 134 | re3 = new RegExp("([^aeiouylsz])\\1$"); 135 | re4 = new RegExp("^" + C + v + "[^aeiouwxy]$"); 136 | if (re2.test(w)) 137 | w = w + "e"; 138 | else if (re3.test(w)) { 139 | re = /.$/; 140 | w = w.replace(re,""); 141 | } 142 | else if (re4.test(w)) 143 | w = w + "e"; 144 | } 145 | } 146 | 147 | // Step 1c 148 | re = /^(.+?)y$/; 149 | if (re.test(w)) { 150 | var fp = re.exec(w); 151 | stem = fp[1]; 152 | re = new RegExp(s_v); 153 | if (re.test(stem)) 154 | w = stem + "i"; 155 | } 156 | 157 | // Step 2 158 | re = /^(.+?)(ational|tional|enci|anci|izer|bli|alli|entli|eli|ousli|ization|ation|ator|alism|iveness|fulness|ousness|aliti|iviti|biliti|logi)$/; 159 | if (re.test(w)) { 160 | var fp = re.exec(w); 161 | stem = fp[1]; 162 | suffix = fp[2]; 163 | re = new RegExp(mgr0); 164 | if (re.test(stem)) 165 | w = stem + step2list[suffix]; 166 | } 167 | 168 | // Step 3 169 | re = /^(.+?)(icate|ative|alize|iciti|ical|ful|ness)$/; 170 | if (re.test(w)) { 171 | var fp = re.exec(w); 172 | stem = fp[1]; 173 | suffix = fp[2]; 174 | re = new RegExp(mgr0); 175 | if (re.test(stem)) 176 | w = stem + step3list[suffix]; 177 | } 178 | 179 | // Step 4 180 | re = /^(.+?)(al|ance|ence|er|ic|able|ible|ant|ement|ment|ent|ou|ism|ate|iti|ous|ive|ize)$/; 181 | re2 = /^(.+?)(s|t)(ion)$/; 182 | if (re.test(w)) { 183 | var fp = re.exec(w); 184 | stem = fp[1]; 185 | re = new RegExp(mgr1); 186 | if (re.test(stem)) 187 | w = stem; 188 | } 189 | else if (re2.test(w)) { 190 | var fp = re2.exec(w); 191 | stem = fp[1] + fp[2]; 192 | re2 = new RegExp(mgr1); 193 | if (re2.test(stem)) 194 | w = stem; 195 | } 196 | 197 | // Step 5 198 | re = /^(.+?)e$/; 199 | if (re.test(w)) { 200 | var fp = re.exec(w); 201 | stem = fp[1]; 202 | re = new RegExp(mgr1); 203 | re2 = new RegExp(meq1); 204 | re3 = new RegExp("^" + C + v + "[^aeiouwxy]$"); 205 | if (re.test(stem) || (re2.test(stem) && !(re3.test(stem)))) 206 | w = stem; 207 | } 208 | re = /ll$/; 209 | re2 = new RegExp(mgr1); 210 | if (re.test(w) && re2.test(w)) { 211 | re = /.$/; 212 | w = w.replace(re,""); 213 | } 214 | 215 | // and turn initial Y back to y 216 | if (firstch == "y") 217 | w = firstch.toLowerCase() + w.substr(1); 218 | return w; 219 | } 220 | } 221 | 222 | 223 | /** 224 | * Search Module 225 | */ 226 | var Search = { 227 | 228 | _index : null, 229 | _queued_query : null, 230 | _pulse_status : -1, 231 | 232 | init : function() { 233 | var params = $.getQueryParameters(); 234 | if (params.q) { 235 | var query = params.q[0]; 236 | $('input[name="q"]')[0].value = query; 237 | this.performSearch(query); 238 | } 239 | }, 240 | 241 | loadIndex : function(url) { 242 | $.ajax({type: "GET", url: url, data: null, success: null, 243 | dataType: "script", cache: true}); 244 | }, 245 | 246 | setIndex : function(index) { 247 | var q; 248 | this._index = index; 249 | if ((q = this._queued_query) !== null) { 250 | this._queued_query = null; 251 | Search.query(q); 252 | } 253 | }, 254 | 255 | hasIndex : function() { 256 | return this._index !== null; 257 | }, 258 | 259 | deferQuery : function(query) { 260 | this._queued_query = query; 261 | }, 262 | 263 | stopPulse : function() { 264 | this._pulse_status = 0; 265 | }, 266 | 267 | startPulse : function() { 268 | if (this._pulse_status >= 0) 269 | return; 270 | function pulse() { 271 | Search._pulse_status = (Search._pulse_status + 1) % 4; 272 | var dotString = ''; 273 | for (var i = 0; i < Search._pulse_status; i++) 274 | dotString += '.'; 275 | Search.dots.text(dotString); 276 | if (Search._pulse_status > -1) 277 | window.setTimeout(pulse, 500); 278 | }; 279 | pulse(); 280 | }, 281 | 282 | /** 283 | * perform a search for something 284 | */ 285 | performSearch : function(query) { 286 | // create the required interface elements 287 | this.out = $('#search-results'); 288 | this.title = $('

' + _('Searching') + '

').appendTo(this.out); 289 | this.dots = $('').appendTo(this.title); 290 | this.status = $('

').appendTo(this.out); 291 | this.output = $('