1
0
Fork 0
mirror of synced 2024-06-02 10:24:39 +12:00
bulk-downloader-for-reddit/tests/integration_tests/test_download_integration.py

443 lines
17 KiB
Python
Raw Normal View History

2021-03-11 20:21:05 +13:00
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
2021-03-11 20:21:05 +13:00
import shutil
2021-03-11 20:21:05 +13:00
from pathlib import Path
2022-12-15 17:04:33 +13:00
from unittest.mock import MagicMock, patch
2021-03-11 20:21:05 +13:00
2022-12-15 17:04:33 +13:00
import prawcore
2021-03-11 20:21:05 +13:00
import pytest
from click.testing import CliRunner
2021-04-12 19:58:32 +12:00
from bdfr.__main__ import cli
2021-03-11 20:21:05 +13:00
2022-12-03 18:11:17 +13:00
does_test_config_exist = Path("./tests/test_config.cfg").exists()
2021-03-11 20:21:05 +13:00
2021-04-23 23:05:21 +12:00
def copy_test_config(run_path: Path):
shutil.copy(Path("./tests/test_config.cfg"), Path(run_path, "test_config.cfg"))
def create_basic_args_for_download_runner(test_args: list[str], run_path: Path):
copy_test_config(run_path)
2021-04-27 14:29:37 +12:00
out = [
2022-12-03 18:11:17 +13:00
"download",
str(run_path),
"-v",
"--config",
str(Path(run_path, "test_config.cfg")),
2022-12-03 18:11:17 +13:00
"--log",
str(Path(run_path, "test_log.txt")),
2021-04-27 14:29:37 +12:00
] + test_args
return out
2021-03-11 20:21:05 +13:00
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
"test_args",
(
["-s", "Mindustry", "-L", 3],
["-s", "r/Mindustry", "-L", 3],
["-s", "r/mindustry", "-L", 3],
["-s", "mindustry", "-L", 3],
["-s", "https://www.reddit.com/r/TrollXChromosomes/", "-L", 3],
["-s", "r/TrollXChromosomes/", "-L", 3],
["-s", "TrollXChromosomes/", "-L", 3],
["-s", "trollxchromosomes", "-L", 3],
["-s", "trollxchromosomes,mindustry,python", "-L", 3],
["-s", "trollxchromosomes, mindustry, python", "-L", 3],
["-s", "trollxchromosomes", "-L", 3, "--time", "day"],
["-s", "trollxchromosomes", "-L", 3, "--sort", "new"],
["-s", "trollxchromosomes", "-L", 3, "--time", "day", "--sort", "new"],
["-s", "trollxchromosomes", "-L", 3, "--search", "women"],
2023-01-07 20:21:25 +13:00
["-s", "trollxchromosomes", "-L", 3, "--time", "week", "--search", "women"],
2022-12-03 18:11:17 +13:00
["-s", "trollxchromosomes", "-L", 3, "--sort", "new", "--search", "women"],
2023-01-07 20:21:25 +13:00
["-s", "trollxchromosomes", "-L", 3, "--time", "week", "--sort", "new", "--search", "women"],
2022-12-03 18:11:17 +13:00
),
)
2021-03-11 20:21:05 +13:00
def test_cli_download_subreddits(test_args: list[str], tmp_path: Path):
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
2021-07-02 16:17:13 +12:00
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "Added submissions from subreddit " in result.output
assert "Downloaded submission" in result.output
2021-07-02 16:17:13 +12:00
2021-09-09 15:43:11 +12:00
@pytest.mark.online
@pytest.mark.reddit
@pytest.mark.slow
2021-09-09 15:43:11 +12:00
@pytest.mark.authenticated
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
"test_args",
(
["-s", "hentai", "-L", 10, "--search", "red", "--authenticate"],
["--authenticate", "--subscribed", "-L", 10],
),
)
2021-09-09 15:43:11 +12:00
def test_cli_download_search_subreddits_authenticated(test_args: list[str], tmp_path: Path):
runner = CliRunner()
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "Added submissions from subreddit " in result.output
assert "Downloaded submission" in result.output
2021-09-09 15:43:11 +12:00
2021-07-02 16:17:13 +12:00
@pytest.mark.online
@pytest.mark.reddit
@pytest.mark.authenticated
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize("test_args", (["--subreddit", "friends", "-L", 10, "--authenticate"],))
2021-07-02 16:17:13 +12:00
def test_cli_download_user_specific_subreddits(test_args: list[str], tmp_path: Path):
runner = CliRunner()
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
2021-03-11 20:21:05 +13:00
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "Added submissions from subreddit " in result.output
2021-03-11 20:21:05 +13:00
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
"test_args",
(
["-l", "6l7778"],
["-l", "https://reddit.com/r/EmpireDidNothingWrong/comments/6l7778/technically_true/"],
["-l", "m3hxzd"], # Really long title used to overflow filename limit
["-l", "m5bqkf"], # Resource leading to a 404
),
)
2021-03-11 20:21:05 +13:00
def test_cli_download_links(test_args: list[str], tmp_path: Path):
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
2021-03-11 20:21:05 +13:00
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
"test_args",
(
["--user", "helen_darten", "-m", "cuteanimalpics", "-L", 10],
["--user", "helen_darten", "-m", "cuteanimalpics", "-L", 10, "--sort", "rising"],
["--user", "helen_darten", "-m", "cuteanimalpics", "-L", 10, "--time", "week"],
["--user", "helen_darten", "-m", "cuteanimalpics", "-L", 10, "--time", "week", "--sort", "rising"],
),
)
2021-03-11 20:21:05 +13:00
def test_cli_download_multireddit(test_args: list[str], tmp_path: Path):
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
2021-03-11 20:21:05 +13:00
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "Added submissions from multireddit " in result.output
2021-03-11 20:21:05 +13:00
2021-03-12 01:18:54 +13:00
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize("test_args", (["--user", "helen_darten", "-m", "xxyyzzqwerty", "-L", 10],))
2021-03-12 01:18:54 +13:00
def test_cli_download_multireddit_nonexistent(test_args: list[str], tmp_path: Path):
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
2021-03-12 01:18:54 +13:00
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "Failed to get submissions for multireddit" in result.output
assert "received 404 HTTP response" in result.output
2021-03-12 01:18:54 +13:00
2021-03-11 20:21:05 +13:00
@pytest.mark.online
@pytest.mark.reddit
@pytest.mark.authenticated
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
"test_args",
(
["--user", "djnish", "--submitted", "--user", "FriesWithThat", "-L", 10],
["--user", "me", "--upvoted", "--authenticate", "-L", 10],
["--user", "me", "--saved", "--authenticate", "-L", 10],
["--user", "me", "--submitted", "--authenticate", "-L", 10],
["--user", "djnish", "--submitted", "-L", 10],
["--user", "djnish", "--submitted", "-L", 10, "--time", "month"],
["--user", "djnish", "--submitted", "-L", 10, "--sort", "controversial"],
),
)
2021-03-11 20:21:05 +13:00
def test_cli_download_user_data_good(test_args: list[str], tmp_path: Path):
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
2021-03-11 20:21:05 +13:00
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "Downloaded submission " in result.output
2021-03-11 20:21:05 +13:00
@pytest.mark.online
@pytest.mark.reddit
@pytest.mark.authenticated
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize("test_args", (["--user", "me", "-L", 10, "--folder-scheme", ""],))
2021-03-11 20:21:05 +13:00
def test_cli_download_user_data_bad_me_unauthenticated(test_args: list[str], tmp_path: Path):
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
2021-03-11 20:21:05 +13:00
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
assert 'To use "me" as a user, an authenticated Reddit instance must be used' in result.output
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize("test_args", (["--subreddit", "python", "-L", 1, "--search-existing"],))
def test_cli_download_search_existing(test_args: list[str], tmp_path: Path):
2022-12-03 18:11:17 +13:00
Path(tmp_path, "test.txt").touch()
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "Calculating hashes for" in result.output
2021-03-13 16:22:22 +13:00
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
"test_args",
(
["--subreddit", "tumblr", "-L", "25", "--skip", "png", "--skip", "jpg"],
["--subreddit", "MaliciousCompliance", "-L", "25", "--skip", "txt"],
["--subreddit", "tumblr", "-L", "10", "--skip-domain", "i.redd.it"],
),
)
2021-06-24 18:14:21 +12:00
def test_cli_download_download_filters(test_args: list[str], tmp_path: Path):
runner = CliRunner()
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert any((string in result.output for string in ("Download filter removed ", "filtered due to URL")))
2021-03-13 16:22:22 +13:00
@pytest.mark.online
@pytest.mark.reddit
2021-03-13 18:11:59 +13:00
@pytest.mark.slow
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize("test_args", (["--subreddit", "all", "-L", "100", "--sort", "new"],))
2021-03-13 16:22:22 +13:00
def test_cli_download_long(test_args: list[str], tmp_path: Path):
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
2021-03-13 16:22:22 +13:00
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2021-03-14 14:11:37 +13:00
2021-03-14 15:03:43 +13:00
@pytest.mark.online
@pytest.mark.reddit
@pytest.mark.slow
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
"test_args",
(
["--user", "sdclhgsolgjeroij", "--submitted", "-L", 10],
["--user", "me", "--upvoted", "-L", 10],
["--user", "sdclhgsolgjeroij", "--upvoted", "-L", 10],
["--subreddit", "submitters", "-L", 10], # Private subreddit
["--subreddit", "donaldtrump", "-L", 10], # Banned subreddit
["--user", "djnish", "--user", "helen_darten", "-m", "cuteanimalpics", "-L", 10],
["--subreddit", "friends", "-L", 10],
["-l", "ijy4ch"], # user deleted post
["-l", "kw4wjm"], # post from banned subreddit
),
)
2021-03-14 15:03:43 +13:00
def test_cli_download_soft_fail(test_args: list[str], tmp_path: Path):
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
2021-03-14 15:03:43 +13:00
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "Downloaded" not in result.output
2021-03-14 15:03:43 +13:00
@pytest.mark.online
@pytest.mark.reddit
@pytest.mark.slow
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
"test_args",
(
["--time", "random"],
["--sort", "random"],
),
)
2021-03-14 15:03:43 +13:00
def test_cli_download_hard_fail(test_args: list[str], tmp_path: Path):
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
2021-03-14 15:03:43 +13:00
result = runner.invoke(cli, test_args)
assert result.exit_code != 0
def test_cli_download_use_default_config(tmp_path: Path):
runner = CliRunner()
test_args = ["download", "-vv", str(tmp_path), "--log", str(Path(tmp_path, "test_log.txt"))]
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize("test_args", (["-l", "6l7778", "--exclude-id", "6l7778"],))
2021-04-05 23:32:39 +12:00
def test_cli_download_links_exclusion(test_args: list[str], tmp_path: Path):
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "in exclusion list" in result.output
assert "Downloaded submission " not in result.output
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
"test_args",
(
["-l", "6l7778", "--skip-subreddit", "EmpireDidNothingWrong"],
["-s", "trollxchromosomes", "--skip-subreddit", "trollxchromosomes", "-L", "3"],
),
)
def test_cli_download_subreddit_exclusion(test_args: list[str], tmp_path: Path):
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "in skip list" in result.output
assert "Downloaded submission " not in result.output
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
"test_args",
(
["--file-scheme", "{TITLE}"],
["--file-scheme", "{TITLE}_test_{SUBREDDIT}"],
),
)
def test_cli_download_file_scheme_warning(test_args: list[str], tmp_path: Path):
runner = CliRunner()
2021-04-27 14:29:37 +12:00
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "Some files might not be downloaded due to name conflicts" in result.output
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
"test_args",
(
["-l", "n9w9fo", "--disable-module", "SelfPost"],
["-l", "nnb9vs", "--disable-module", "VReddit"],
),
)
def test_cli_download_disable_modules(test_args: list[str], tmp_path: Path):
runner = CliRunner()
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "skipped due to disabled module" in result.output
assert "Downloaded submission" not in result.output
2021-07-05 18:58:33 +12:00
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
2021-07-05 18:58:33 +12:00
def test_cli_download_include_id_file(tmp_path: Path):
2022-12-03 18:11:17 +13:00
test_file = Path(tmp_path, "include.txt")
test_args = ["--include-id-file", str(test_file)]
test_file.write_text("odr9wg\nody576")
2021-07-05 18:58:33 +12:00
runner = CliRunner()
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "Downloaded submission" in result.output
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize("test_args", (["--ignore-user", "ArjanEgges", "-l", "m3hxzd"],))
def test_cli_download_ignore_user(test_args: list[str], tmp_path: Path):
runner = CliRunner()
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert "Downloaded submission" not in result.output
assert "being an ignored user" in result.output
2022-07-23 15:59:35 +12:00
@pytest.mark.online
@pytest.mark.reddit
2022-12-03 18:11:17 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
("test_args", "was_filtered"),
(
(["-l", "ljyy27", "--min-score", "50"], True),
(["-l", "ljyy27", "--min-score", "1"], False),
(["-l", "ljyy27", "--max-score", "1"], True),
(["-l", "ljyy27", "--max-score", "100"], False),
),
)
2022-07-23 15:59:35 +12:00
def test_cli_download_score_filter(test_args: list[str], was_filtered: bool, tmp_path: Path):
runner = CliRunner()
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
2022-12-03 18:11:17 +13:00
assert ("filtered due to score" in result.output) == was_filtered
2022-12-15 17:04:33 +13:00
2023-01-04 22:07:31 +13:00
@pytest.mark.online
@pytest.mark.reddit
2022-12-15 17:04:33 +13:00
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
("test_args", "response"),
(
(["--user", "nasa", "--submitted"], 502),
(["--user", "nasa", "--submitted"], 504),
2022-12-15 17:04:33 +13:00
),
)
2023-01-04 22:49:50 +13:00
def test_cli_download_user_reddit_server_error(test_args: list[str], response: int, tmp_path: Path):
2022-12-15 17:04:33 +13:00
runner = CliRunner()
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
with patch("bdfr.connector.sleep", return_value=None):
with patch(
"bdfr.connector.RedditConnector.check_user_existence",
side_effect=prawcore.exceptions.ResponseException(MagicMock(status_code=response)),
):
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
assert f"received {response} HTTP response" in result.output
2023-01-04 22:49:09 +13:00
@pytest.mark.online
@pytest.mark.reddit
@pytest.mark.skipif(not does_test_config_exist, reason="A test config file is required for integration tests")
@pytest.mark.parametrize(
"test_args",
(
["-l", "102vd5i", "--filename-restriction-scheme", "windows"],
["-l", "m3hxzd", "--filename-restriction-scheme", "windows"],
),
)
def test_cli_download_explicit_filename_restriction_scheme(test_args: list[str], tmp_path: Path):
runner = CliRunner()
test_args = create_basic_args_for_download_runner(test_args, tmp_path)
result = runner.invoke(cli, test_args)
assert result.exit_code == 0
assert "Downloaded submission" in result.output
assert "Forcing Windows-compatible filenames" in result.output