2021-02-11 12:08:47 +13:00
|
|
|
#!/usr/bin/env python3
|
|
|
|
# coding=utf-8
|
|
|
|
|
|
|
|
from pathlib import Path
|
2021-03-10 17:39:01 +13:00
|
|
|
from typing import Optional
|
|
|
|
from unittest.mock import MagicMock
|
2021-02-11 12:08:47 +13:00
|
|
|
|
|
|
|
import praw.models
|
|
|
|
import pytest
|
|
|
|
|
|
|
|
from bulkredditdownloader.file_name_formatter import FileNameFormatter
|
|
|
|
from bulkredditdownloader.resource import Resource
|
|
|
|
|
|
|
|
|
|
|
|
@pytest.fixture()
|
2021-03-10 17:39:01 +13:00
|
|
|
def submission() -> MagicMock:
|
|
|
|
test = MagicMock()
|
2021-02-11 12:08:47 +13:00
|
|
|
test.title = 'name'
|
|
|
|
test.subreddit.display_name = 'randomreddit'
|
|
|
|
test.author.name = 'person'
|
|
|
|
test.id = '12345'
|
|
|
|
test.score = 1000
|
|
|
|
test.link_flair_text = 'test_flair'
|
|
|
|
test.created_utc = 123456789
|
|
|
|
return test
|
|
|
|
|
|
|
|
|
|
|
|
@pytest.fixture()
|
2021-02-15 22:16:51 +13:00
|
|
|
def reddit_submission(reddit_instance) -> praw.models.Submission:
|
|
|
|
return reddit_instance.submission(id='lgilgt')
|
2021-02-11 12:08:47 +13:00
|
|
|
|
|
|
|
|
|
|
|
@pytest.mark.parametrize(('format_string', 'expected'), (('{SUBREDDIT}', 'randomreddit'),
|
|
|
|
('{REDDITOR}', 'person'),
|
|
|
|
('{POSTID}', '12345'),
|
|
|
|
('{UPVOTES}', '1000'),
|
|
|
|
('{FLAIR}', 'test_flair'),
|
|
|
|
('{DATE}', '123456789'),
|
|
|
|
('{REDDITOR}_{TITLE}_{POSTID}', 'person_name_12345')
|
|
|
|
))
|
2021-03-10 17:39:01 +13:00
|
|
|
def test_format_name_mock(format_string: str, expected: str, submission: MagicMock):
|
2021-02-11 12:08:47 +13:00
|
|
|
result = FileNameFormatter._format_name(submission, format_string)
|
|
|
|
assert result == expected
|
|
|
|
|
|
|
|
|
2021-03-02 17:06:21 +13:00
|
|
|
@pytest.mark.parametrize(('test_string', 'expected'), (
|
|
|
|
('', False),
|
|
|
|
('test', False),
|
|
|
|
('{POSTID}', True),
|
|
|
|
('POSTID', False),
|
|
|
|
('{POSTID}_test', True),
|
|
|
|
('test_{TITLE}', True),
|
|
|
|
('TITLE_POSTID', False),
|
|
|
|
))
|
|
|
|
def test_check_format_string_validity(test_string: str, expected: bool):
|
|
|
|
result = FileNameFormatter.validate_string(test_string)
|
|
|
|
assert result == expected
|
|
|
|
|
|
|
|
|
2021-02-26 22:09:25 +13:00
|
|
|
@pytest.mark.online
|
2021-02-26 22:19:12 +13:00
|
|
|
@pytest.mark.reddit
|
2021-02-11 12:08:47 +13:00
|
|
|
@pytest.mark.parametrize(('format_string', 'expected'),
|
|
|
|
(('{SUBREDDIT}', 'Mindustry'),
|
|
|
|
('{REDDITOR}', 'Gamer_player_boi'),
|
|
|
|
('{POSTID}', 'lgilgt'),
|
|
|
|
('{FLAIR}', 'Art'),
|
|
|
|
('{SUBREDDIT}_{TITLE}', 'Mindustry_Toxopid that is NOT humane >:('),
|
|
|
|
('{REDDITOR}_{TITLE}_{POSTID}', 'Gamer_player_boi_Toxopid that is NOT humane >:(_lgilgt')
|
|
|
|
))
|
|
|
|
def test_format_name_real(format_string: str, expected: str, reddit_submission: praw.models.Submission):
|
|
|
|
result = FileNameFormatter._format_name(reddit_submission, format_string)
|
|
|
|
assert result == expected
|
|
|
|
|
|
|
|
|
2021-02-26 22:09:25 +13:00
|
|
|
@pytest.mark.online
|
2021-02-26 22:19:12 +13:00
|
|
|
@pytest.mark.reddit
|
2021-02-11 12:08:47 +13:00
|
|
|
@pytest.mark.parametrize(('format_string_directory', 'format_string_file', 'expected'),
|
|
|
|
(('{SUBREDDIT}', '{POSTID}', 'test/Mindustry/lgilgt.png'),
|
|
|
|
('{SUBREDDIT}', '{TITLE}_{POSTID}',
|
|
|
|
'test/Mindustry/Toxopid that is NOT humane >:(_lgilgt.png'),
|
|
|
|
('{SUBREDDIT}', '{REDDITOR}_{TITLE}_{POSTID}',
|
|
|
|
'test/Mindustry/Gamer_player_boi_Toxopid that is NOT humane >:(_lgilgt.png')
|
|
|
|
))
|
|
|
|
def test_format_full(
|
|
|
|
format_string_directory: str,
|
|
|
|
format_string_file: str,
|
|
|
|
expected: str,
|
|
|
|
reddit_submission: praw.models.Submission):
|
2021-02-26 22:09:25 +13:00
|
|
|
test_resource = Resource(reddit_submission, 'i.reddit.com/blabla.png')
|
2021-02-11 12:08:47 +13:00
|
|
|
test_formatter = FileNameFormatter(format_string_file, format_string_directory)
|
2021-03-13 23:18:30 +13:00
|
|
|
result = test_formatter.format_path(test_resource, Path('test'))
|
2021-02-11 12:08:47 +13:00
|
|
|
assert str(result) == expected
|
2021-03-10 17:39:01 +13:00
|
|
|
|
|
|
|
|
2021-03-14 14:10:26 +13:00
|
|
|
@pytest.mark.online
|
|
|
|
@pytest.mark.reddit
|
|
|
|
@pytest.mark.parametrize(('format_string_directory', 'format_string_file'), (
|
|
|
|
('{SUBREDDIT}', '{POSTID}'),
|
|
|
|
('{SUBREDDIT}', '{UPVOTES}'),
|
|
|
|
('{SUBREDDIT}', '{UPVOTES}{POSTID}'),
|
|
|
|
))
|
|
|
|
def test_format_full_conform(
|
|
|
|
format_string_directory: str,
|
|
|
|
format_string_file: str,
|
|
|
|
reddit_submission: praw.models.Submission):
|
|
|
|
test_resource = Resource(reddit_submission, 'i.reddit.com/blabla.png')
|
|
|
|
test_formatter = FileNameFormatter(format_string_file, format_string_directory)
|
|
|
|
test_formatter.format_path(test_resource, Path('test'))
|
|
|
|
|
|
|
|
|
2021-03-10 17:39:01 +13:00
|
|
|
@pytest.mark.online
|
|
|
|
@pytest.mark.reddit
|
|
|
|
@pytest.mark.parametrize(('format_string_directory', 'format_string_file', 'index', 'expected'),
|
|
|
|
(('{SUBREDDIT}', '{POSTID}', None, 'test/Mindustry/lgilgt.png'),
|
|
|
|
('{SUBREDDIT}', '{POSTID}', 1, 'test/Mindustry/lgilgt_1.png'),
|
|
|
|
('{SUBREDDIT}', '{POSTID}', 2, 'test/Mindustry/lgilgt_2.png'),
|
|
|
|
('{SUBREDDIT}', '{TITLE}_{POSTID}', 2,
|
|
|
|
'test/Mindustry/Toxopid that is NOT humane >:(_lgilgt_2.png'),
|
|
|
|
))
|
|
|
|
def test_format_full_with_index_suffix(
|
|
|
|
format_string_directory: str,
|
|
|
|
format_string_file: str,
|
|
|
|
index: Optional[int],
|
|
|
|
expected: str,
|
|
|
|
reddit_submission: praw.models.Submission):
|
|
|
|
test_resource = Resource(reddit_submission, 'i.reddit.com/blabla.png')
|
|
|
|
test_formatter = FileNameFormatter(format_string_file, format_string_directory)
|
2021-03-13 23:18:30 +13:00
|
|
|
result = test_formatter.format_path(test_resource, Path('test'), index)
|
2021-03-10 17:39:01 +13:00
|
|
|
assert str(result) == expected
|
|
|
|
|
|
|
|
|
|
|
|
def test_format_multiple_resources():
|
|
|
|
mocks = []
|
|
|
|
for i in range(1, 5):
|
|
|
|
new_mock = MagicMock()
|
|
|
|
new_mock.url = 'https://example.com/test.png'
|
|
|
|
new_mock.extension = '.png'
|
|
|
|
new_mock.source_submission.title = 'test'
|
|
|
|
mocks.append(new_mock)
|
|
|
|
test_formatter = FileNameFormatter('{TITLE}', '')
|
|
|
|
results = test_formatter.format_resource_paths(mocks, Path('.'))
|
|
|
|
results = set([str(res[0]) for res in results])
|
|
|
|
assert results == {'test_1.png', 'test_2.png', 'test_3.png', 'test_4.png'}
|
2021-03-13 14:13:36 +13:00
|
|
|
|
|
|
|
|
|
|
|
@pytest.mark.parametrize(('test_filename', 'test_ending'), (
|
|
|
|
('A' * 300, '.png'),
|
|
|
|
('A' * 300, '_1.png'),
|
|
|
|
('a' * 300, '_1000.jpeg'),
|
2021-03-13 15:39:54 +13:00
|
|
|
('😍💕✨' * 100, '_1.png'),
|
2021-03-13 14:13:36 +13:00
|
|
|
))
|
|
|
|
def test_limit_filename_length(test_filename: str, test_ending: str):
|
|
|
|
result = FileNameFormatter._limit_file_name_length(test_filename, test_ending)
|
|
|
|
assert len(result) <= 255
|
2021-03-13 15:39:54 +13:00
|
|
|
assert len(result.encode('utf-8')) <= 255
|
|
|
|
assert isinstance(result, str)
|
2021-03-13 14:13:36 +13:00
|
|
|
|
|
|
|
|
2021-03-27 00:38:04 +13:00
|
|
|
@pytest.mark.parametrize(('test_filename', 'test_ending', 'expected_end'), (
|
|
|
|
('test_aaaaaa', '_1.png', 'test_aaaaaa_1.png'),
|
|
|
|
('test_aaaaaa', '.png', 'test_aaaaaa.png'),
|
|
|
|
('test', '_1.png', 'test_1.png'),
|
|
|
|
('test_m1hqw6', '_1.png', 'test_m1hqw6_1.png'),
|
|
|
|
('A' * 300 + '_bbbccc', '.png', '_bbbccc.png'),
|
|
|
|
('A' * 300 + '_bbbccc', '_1000.jpeg', '_bbbccc_1000.jpeg'),
|
|
|
|
('😍💕✨' * 100 + '_aaa1aa', '_1.png', '_aaa1aa_1.png'),
|
|
|
|
))
|
|
|
|
def test_preserve_id_append_when_shortening(test_filename: str, test_ending: str, expected_end: str):
|
|
|
|
result = FileNameFormatter._limit_file_name_length(test_filename, test_ending)
|
|
|
|
assert len(result) <= 255
|
|
|
|
assert len(result.encode('utf-8')) <= 255
|
|
|
|
assert isinstance(result, str)
|
|
|
|
assert result.endswith(expected_end)
|
|
|
|
|
|
|
|
|
2021-03-27 00:12:52 +13:00
|
|
|
def test_shorten_filenames(tmp_path: Path):
|
2021-03-13 14:13:36 +13:00
|
|
|
test_submission = MagicMock()
|
|
|
|
test_submission.title = 'A' * 300
|
|
|
|
test_submission.author.name = 'test'
|
|
|
|
test_submission.subreddit.display_name = 'test'
|
|
|
|
test_submission.id = 'BBBBBB'
|
|
|
|
test_resource = Resource(test_submission, 'www.example.com/empty', '.jpeg')
|
|
|
|
test_formatter = FileNameFormatter('{REDDITOR}_{TITLE}_{POSTID}', '{SUBREDDIT}')
|
2021-03-13 23:18:30 +13:00
|
|
|
result = test_formatter.format_path(test_resource, tmp_path)
|
2021-03-13 14:13:36 +13:00
|
|
|
result.parent.mkdir(parents=True)
|
|
|
|
result.touch()
|
2021-03-22 17:21:56 +13:00
|
|
|
|
|
|
|
|
|
|
|
@pytest.mark.parametrize(('test_string', 'expected'), (
|
|
|
|
('test', 'test'),
|
2021-03-28 00:14:08 +13:00
|
|
|
('test😍', 'test'),
|
2021-03-22 17:21:56 +13:00
|
|
|
('test.png', 'test.png'),
|
|
|
|
('test*', 'test'),
|
|
|
|
('test**', 'test'),
|
|
|
|
('test?*', 'test'),
|
|
|
|
('test_???.png', 'test_.png'),
|
2021-03-28 00:14:08 +13:00
|
|
|
('test_???😍.png', 'test_.png'),
|
2021-03-22 17:21:56 +13:00
|
|
|
))
|
|
|
|
def test_format_file_name_for_windows(test_string: str, expected: str):
|
|
|
|
result = FileNameFormatter._format_for_windows(test_string)
|
|
|
|
assert result == expected
|
2021-03-28 00:14:08 +13:00
|
|
|
|
|
|
|
|
|
|
|
@pytest.mark.parametrize(('test_string', 'expected'), (
|
|
|
|
('test', 'test'),
|
|
|
|
('test😍', 'test'),
|
|
|
|
('😍', ''),
|
|
|
|
))
|
|
|
|
def test_strip_emojies(test_string: str, expected: str):
|
|
|
|
result = FileNameFormatter._strip_emojis(test_string)
|
|
|
|
assert result == expected
|