2016-12-07 12 views
1

私は実行する前にウェブからたくさんのファイルをダウンロードしなければならないプログラムを書いているので、すべてのファイルをダウンロードして"初期化 "init_programと呼ばれるプログラムは、githubのgistfilesへのURLを持っているdictsを介して動作します。 URLを取得し、urllib2をダウンロードしてダウンロードします。私はすべてのファイルを追加することはできませんが、repo hereをクローンとして試してみることができます。ここでは要点からファイルを作成する機能があります:ウェブからのファイルダウンロードの処理速度を速める

def init_program(): 
    """ Initialize the program and allow all the files to be downloaded 
     This will take awhile to process, but I'm working on the processing 
     speed """ 

    downloaded_wordlists = [] # Used to count the amount of items downloaded 
    downloaded_rainbow_tables = [] 

    print("\n") 
    banner("Initializing program and downloading files, this may take awhile..") 
    print("\n") 

    # INIT_FILE is a file that will contain "false" if the program is not initialized 
    # And "true" if the program is initialized 
    with open(INIT_FILE) as data: 
     if data.read() == "false": 
      for item in GIST_DICT_LINKS.keys(): 
       sys.stdout.write("\rDownloading {} out of {} wordlists.. ".format(len(downloaded_wordlists) + 1, 
                        len(GIST_DICT_LINKS.keys()))) 
       sys.stdout.flush() 
       new_wordlist = open("dicts/included_dicts/wordlists/{}.txt".format(item), "a+") 
       # Download the wordlists and save them into a file 
       wordlist_data = urllib2.urlopen(GIST_DICT_LINKS[item]) 
       new_wordlist.write(wordlist_data.read()) 
       downloaded_wordlists.append(item + ".txt") 
       new_wordlist.close() 

      print("\n") 
      banner("Done with wordlists, moving to rainbow tables..") 
      print("\n") 

      for table in GIST_RAINBOW_LINKS.keys(): 
       sys.stdout.write("\rDownloading {} out of {} rainbow tables".format(len(downloaded_rainbow_tables) + 1, 
                        len(GIST_RAINBOW_LINKS.keys()))) 
       new_rainbowtable = open("dicts/included_dicts/rainbow_tables/{}.rtc".format(table)) 
       # Download the rainbow tables and save them into a file 
       rainbow_data = urllib2.urlopen(GIST_RAINBOW_LINKS[table]) 
       new_rainbowtable.write(rainbow_data.read()) 
       downloaded_rainbow_tables.append(table + ".rtc") 
       new_rainbowtable.close() 

      open(data, "w").write("true").close() # Will never be initialized again 
     else: 
      pass 

    return downloaded_wordlists, downloaded_rainbow_tables 

この作品、はい、しかし、それは、各ファイルは、その中に、少なくとも100,000行を持っている、ファイルのサイズのため、非常に遅いです。この機能を高速化してより使いやすくするにはどうすればよいですか?

+0

ええと、それはあなたのWiFi接続によって異なります。 Wi-Fiを改善することを除いて、これをスピードアップする方法はほとんどありません。いいにくいのですが。 – Qwerty

+0

@QWERTYスレッドでも?私はこれが遅いことを意味するええ、それは最終的にそれの価値があるでしょうが、それは遅い初期化プロセスです.. – papasmurf

+2

まあ... http://stackoverflow.com/a/9010299/2308683 –

答えて

1

何週間も前に私は多くの巨大なファイルをダウンロードする必要があったが、単純な純粋なPythonソリューションではダウンロードの最適化という点では十分ではなかった。だから私はAxelた -

LinuxやUnix用ライトのコマンドラインダウンロードアクセラレータ

をアクセルとは何ですか?

Axelは、DownThemAllや他の有名な プログラムと同様に、1つのファイルに対して複数の 接続を使用してダウンロードプロセスを高速化しようとします。 1回のダウンロードで複数のミラーを使用することもできます。

Axelを使用すると、インターネットからファイルを高速に取得できます。したがって、Axelは のダウンロード速度を最大60%まで向上させることができます(おおよそ、 テストに従う)。 axelとして

Usage: axel [options] url1 [url2] [url...] 

--max-speed=x  -s x Specify maximum speed (bytes per second) 
--num-connections=x -n x Specify maximum number of connections 
--output=f  -o f Specify local output file 
--search[=x]  -S [x] Search for mirrors and download from x servers 
--header=x  -H x Add header string 
--user-agent=x  -U x Set user agent 
--no-proxy  -N Just don't use any proxy server 
--quiet   -q Leave stdout alone 
--verbose  -v More status information 
--alternate  -a Alternate progress indicator 
--help   -h This information 
--version  -V Version information 

Cで書かれたとPythonのためのC拡張機能はありませんので、私は外部から彼を実行するためにsubprocessモジュールを使用して私のために完璧に動作しています。

あなたはこのような何かを行うことができます。

cmd = ['/usr/local/bin/axel', '-n', str(n_connections), '-o', 
       "{0}".format(filename), url] 
process = subprocess.Popen(cmd,stdin=subprocess.PIPE, stdout=subprocess.PIPE) 

また、標準出力の出力を解析し、各ダウンロードの進捗状況を解析することができます。

while True: 
     line = process.stdout.readline() 
     progress = YOUR_GREAT_REGEX.match(line).groups() 
     ... 

+0

これは、ホスティングサイトがパラレルダウンロードをサポートしている場合にのみ有効です –

+0

これは本当ですが、「最も」の場合に役立ちます。しかし残念ながら、それは銀色の弾丸ではありません。 – GustavoIP

+0

@ GustavolP私はWindowsマシンでも作業しています。これは天才的なことですが、+1 – papasmurf

0

あなたは各ダウンロードを待ちながらブロックしています。したがって、合計時間は各ダウンロードの往復時間の合計です。あなたのコードはネットワークトラフィックを待つのに多くの時間を費やすでしょう。これを改善する1つの方法は、各応答を待つ間にブロックすることではありません。これはいくつかの方法で行うことができます。例えば、それぞれの要求を別のスレッド(またはプロセス)に渡すか、イベントループとコルーチンを使用します。スレッドとasyncioモジュールを読み上げてください。

+0

それぞれのダウンロードを待っている間にブロックすることによって何を意味していますか? – papasmurf

+1

urlopen()に続けてread()を指定すると、接続のオープンを待っていること、送信要求と応答が到着することを意味します。このネットワークトラフィックはかなりの時間がかかる可能性が高く、ほとんどの時間はネットワークトラフィックを待っています。たくさんのリクエストがあったときに、最初のリクエストに応答するのを待たずに、次のリクエストを開始します。 –

+0

だから私はそれをどのように提案するのですか?スレッドのキューを作成し、必要なときにスレッドをプルするだけです。 – papasmurf

関連する問題