Pythonでウェブスクレイピングしてプリンを買い占めたい時のScrapyのVscodeデバッグ構成

# やりたいこと

:custard:「世界中のプリンをマロが…」
:custard:「おほんっ、間違えたでおじゃる」
:custard:「Scrapyをステップ実行で解析したいでおじゃる。ブレークポイントを使わせてたも！」

# あらすじ

PythonでWebスクレイピングをするなら、とりあえずScrapyです。Scrapyはスクレイピングのためのフレームワークです。ところが、[チュートリアル](https://doc-ja-scrapy.readthedocs.io/ja/latest/intro/tutorial.html)から順に進めていくと、クロールするときのデバッグが難しいことに気が付きます。さて、どうやって解決するのでしょうか？

# スクレイピングをしよう

:custard:「ぬるっふっふっふっふっふっふっふ、世界中から買い占めるでおじゃる」
:custard:「ぬるっふっふっふっふっふっふっふ」
:spider: 「（なんでしょう？エイリアン？世界侵略？？）」
:spider: 「（！！）」

:spider: 「おじゃ様！なにをしておられるんですか？」
:custard: 「プリンの販売情報を自動取得しようと思っての、Webスクレイピングしておるのじゃ」
:spider: 「（おじゃ様が成長しておられます！プリン如きのためとは言え素晴らしいです！）」
:spider: 「それは名案にございます！」
:custard: 「しかし、困っておっての、やはり、まろには、ちと早すぎたのかも知れんの」
:spider: 「（おじゃ様せっかくの成長のチャンス！ここは引き伸ばさねば！）」

# 環境

- Pipenv
- WSL2 : Debian
- Python 3.9
- VScode Latest

# 問題点

:spider: 「どこで困っておられるのですか？」
:custard: 「スパイダーにクロールさせるには、CLIで実行オプションを付けるでおじゃるがの」
:spider: 「はい」
:custard: 「こんな感じじゃの」

```
scrapy crawl myspider
```
:spider: 「これは順を追って作業するのに便利でございますね」
:custard: 「そちは良く分かっておるようじゃの」
:spider: 「光栄にございます」
:custard: 「しかし、vscodeでPythonを使う時は、とりあえずCurrentFile実行との設定をしておるのじゃ。」
:custard: 「そちも、こう`launch.json`に以下の設定を入れておるのではないかの？」

```json-doc:./.vscode/launch.json
{
    "version": "0.2.0",
    "configurations": [
        {
            "name": "Python: Current File",
            "type": "python",
            "request": "launch",
            "program": "${file}",
            "console": "integratedTerminal"
        }
    ]
}
```

:spider:「わたくしもそうでございますよ、おじゃ様？何か問題でも？」
:custard:「まろも、簡単だとタカを括っておったのでおじゃる。」
:custard:「これでは、スパイダーを書いたファイルをデバッグしようとしても」
:custard:「『クラスに構文エラーがあるか？』くらいしか分からぬでおじゃる。」
:spider:「たしかに難しいでございますね」

# 解決方法

:spider: 「それでは、新しくデバッグ構成を追加してみてはいかがでしょう？」
:custard: 「はて？Debug構成の追加とな」
:spider: 「デバッグボタンの横のドロップダウンリストからスパイダー専用を選べるようにいたしましょう」
:custard: 「おじゃ、それは面白そうじゃの」
:spider: 「こんな感じの見た目を目標に致しましょう」

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/134703/398a36ca-0020-8e97-9021-bc21022c42e1.png)

:custard:「これならスパイダーを編集しているときに、『F5』ショートカットキーが使えそうじゃの」
:spider:「さすが、おじゃ様、お気付きになられましたか」
:custard:「しかし、スパイダーがたくさんいる時はどうするのじゃ？」
:spider:「それは、こちらをご覧くださいませ」

```diff_jsondoc:./.vscode/launch.json
{
    "version": "0.2.0",
    "configurations": [
        {
            "name": "Python: Current File",
            "type": "python",
            "request": "launch",
            "program": "${file}",
            "console": "integratedTerminal"
+       },
+       {
+            "name": "Scrapy: Current Spider",
+            "type": "python",
+            "request": "launch",
+            "program": "crawl.py",
+            "args": [
+                "${fileBasenameNoExtension}"
+            ],
+            "console": "integratedTerminal"
+        }
    ]
}
```

:custard:「デバッグ構成が１つ増えて…」
:custard:「おじゃ！編集中のスパイダーのファイル名を`crawl.py`に引数として渡しておるの。」
:custard:「これなら、スパイダーが増えても、名前を変えてもデバッグ構成は１つで済みそうじゃの」
:spider:「そうでございます」
:spider:「よくお気づきになられました。わたくし感激にございます」
:custard:「しかし`crawl.py`とは一体何なのじゃ？」
:spider:「それについては、こちらにございます」

```py:./crawl.py
from scrapy.cmdline import execute
import sys

args = sys.argv

execute(['scrapy','crawl', args[1]])
```

:custard:「おじゃ、scrapy謹製の実行ツール`scrapy.cmdline`じゃの。」
:spider:「はい」
:spider:「それが鍵にございます」

:custard:「さあ、説明も終わったし、やれやれじゃの。」
:spider: 「そうですね、おじゃ様。本日はおつかれさまでございます。」
:spider: 「（あれ？これはまずい流れではないでしょうか？）」
:custard:「さあ、プリンでおじゃる！プリンじゃプリンじゃー♪」
:spider: 「（ああ、やはり）」
:custard:「なぜ、しょげておるのじゃ？」
:spider:「おじゃ様？スクレイピングは？」
:custard:「腹が減ってはスクレイピングは出来ぬでおじゃる」
:custard:「おぬしにプリンは、やらぬがの」

# まとめ

おじゃる。

**Excelsior!**

:spider: 「ちなみにScrapyからNocodeへ乗り換えるならOctparseがオススメにございます。」

https://www.octoparse.jp/

:spider: 「そしてScrapyの一般的なデバッグ方法はこちらにございます。」

https://docs.scrapy.org/en/latest/topics/debug.html