summaryrefslogtreecommitdiff
path: root/tests/unit/browser/test_navigate.py
blob: 147b77079c419725890fc5579ef3bf925e8c2b11 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
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
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
# Copyright 2014-2021 Florian Bruhin (The Compiler) <mail@qutebrowser.org>
#
# SPDX-License-Identifier: GPL-3.0-or-later

import pytest

from qutebrowser.qt.core import QUrl

from qutebrowser.browser import navigate
from qutebrowser.utils import urlutils


@pytest.mark.usefixtures('config_stub')
class TestIncDec:

    @pytest.mark.parametrize('incdec', ['increment', 'decrement'])
    @pytest.mark.parametrize('value', [
        '{}foo', 'foo{}', 'foo{}bar', '42foo{}'
    ])
    @pytest.mark.parametrize('url', [
        'http://example.com:80/v1/path/{}/test',
        'http://example.com:80/v1/query_test?value={}',
        'http://example.com:80/v1/anchor_test#{}',
        'http://host_{}_test.com:80',
        'http://m4ny.c0m:80/number5/3very?where=yes#{}',

        # Make sure that FullyDecoded is not used (to avoid losing information)
        'http://localhost/%3A{}',
        'http://localhost/:{}',
        'http://localhost/?v=%3A{}',
        'http://localhost/?v=:{}',
        'http://localhost/#%3A{}',
        'http://localhost/#:{}',

        # Make sure that spaces in paths work
        'http://example.com/path with {} spaces',
    ])
    def test_incdec(self, incdec, value, url, config_stub):
        if (value == '{}foo' and
                url == 'http://example.com/path with {} spaces'):
            pytest.xfail("https://github.com/qutebrowser/qutebrowser/issues/4917")

        config_stub.val.url.incdec_segments = ['host', 'path', 'query',
                                               'anchor']

        # The integer used should not affect test output, as long as it's
        # bigger than 1
        # 20 was chosen by dice roll, guaranteed to be random
        base_value = value.format(20)
        if incdec == 'increment':
            expected_value = value.format(21)
        else:
            expected_value = value.format(19)

        base_url = QUrl(url.format(base_value))
        expected_url = QUrl(url.format(expected_value))

        assert navigate.incdec(base_url, 1, incdec) == expected_url

    def test_port(self, config_stub):
        config_stub.val.url.incdec_segments = ['port']
        base_url = QUrl('http://localhost:8000')
        new_url = navigate.incdec(base_url, 1, 'increment')
        assert new_url == QUrl('http://localhost:8001')
        new_url = navigate.incdec(base_url, 1, 'decrement')
        assert new_url == QUrl('http://localhost:7999')

    def test_port_default(self, config_stub):
        """Test that a default port (with url.port() == -1) is not touched."""
        config_stub.val.url.incdec_segments = ['port']
        base_url = QUrl('http://localhost')
        with pytest.raises(navigate.Error):
            navigate.incdec(base_url, 1, 'increment')

    @pytest.mark.parametrize('inc_or_dec', ['increment', 'decrement'])
    @pytest.mark.parametrize('value', [
        '{}foo', 'foo{}', 'foo{}bar', '42foo{}'
    ])
    @pytest.mark.parametrize('url', [
        'http://example.com:80/v1/path/{}/test',
        'http://example.com:80/v1/query_test?value={}',
        'http://example.com:80/v1/anchor_test#{}',
        'http://host_{}_test.com:80',
        'http://m4ny.c0m:80/number5/3very?where=yes#{}',
    ])
    @pytest.mark.parametrize('count', [1, 5, 100])
    def test_count(self, inc_or_dec, value, url, count, config_stub):
        config_stub.val.url.incdec_segments = ['host', 'path', 'query',
                                               'anchor']
        base_value = value.format(20)
        if inc_or_dec == 'increment':
            expected_value = value.format(20 + count)
        else:
            if count > 20:
                return
            expected_value = value.format(20 - count)

        base_url = QUrl(url.format(base_value))
        expected_url = QUrl(url.format(expected_value))
        new_url = navigate.incdec(base_url, count, inc_or_dec)

        assert new_url == expected_url

    @pytest.mark.parametrize('number, expected, inc_or_dec', [
        ('01', '02', 'increment'),
        ('09', '10', 'increment'),
        ('009', '010', 'increment'),
        ('02', '01', 'decrement'),
        ('10', '9', 'decrement'),
        ('010', '009', 'decrement')
    ])
    def test_leading_zeroes(self, number, expected, inc_or_dec, config_stub):
        config_stub.val.url.incdec_segments = ['path']
        url = 'http://example.com/{}'
        base_url = QUrl(url.format(number))
        expected_url = QUrl(url.format(expected))
        new_url = navigate.incdec(base_url, 1, inc_or_dec)
        assert new_url == expected_url

    @pytest.mark.parametrize('url, segments, expected', [
        ('http://ex4mple.com/test_4?page=3#anchor2', ['host'],
         'http://ex5mple.com/test_4?page=3#anchor2'),
        ('http://ex4mple.com/test_4?page=3#anchor2', ['host', 'path'],
         'http://ex4mple.com/test_5?page=3#anchor2'),
        ('http://ex4mple.com/test_4?page=3#anchor5', ['host', 'path', 'query'],
         'http://ex4mple.com/test_4?page=4#anchor5'),
    ])
    def test_segment_ignored(self, url, segments, expected, config_stub):
        config_stub.val.url.incdec_segments = segments
        new_url = navigate.incdec(QUrl(url), 1, 'increment')
        assert new_url == QUrl(expected)

    @pytest.mark.parametrize('url', [
        "http://example.com/long/path/but/no/number",
        "http://ex4mple.com/number/in/hostname",
        "http://example.com:42/number/in/port",
        "http://www2.example.com/number/in/subdomain",
        "http://example.com/%C3%B6/urlencoded/data",
        "http://example.com/number/in/anchor#5",
        "http://www2.ex4mple.com:42/all/of/the/%C3%A4bove#5",
        "http://localhost/url_encoded_in_query/?v=%3A",
        "http://localhost/url_encoded_in_anchor/#%3A",
    ])
    def test_no_number(self, url):
        with pytest.raises(navigate.Error):
            navigate.incdec(QUrl(url), 1, "increment")

    @pytest.mark.parametrize('url, count', [
        ('http://example.com/page_0.html', 1),
        ('http://example.com/page_1.html', 2),
    ])
    def test_number_below_0(self, url, count):
        with pytest.raises(navigate.Error):
            navigate.incdec(QUrl(url), count, 'decrement')

    def test_invalid_url(self):
        with pytest.raises(urlutils.InvalidUrlError):
            navigate.incdec(QUrl(), 1, "increment")

    def test_wrong_mode(self):
        """Test if incdec rejects a wrong parameter for inc_or_dec."""
        valid_url = QUrl("http://example.com/0")
        with pytest.raises(ValueError):
            navigate.incdec(valid_url, 1, "foobar")


class TestUp:

    @pytest.mark.parametrize('url_suffix, count, expected_suffix', [
        ('/one/two/three', 1, '/one/two'),
        ('/one/two/three?foo=bar', 1, '/one/two'),
        ('/one/two/three', 2, '/one'),
        ('/one/two%2Fthree', 1, '/one'),
        ('/one/two%2Fthree/four', 1, '/one/two%2Fthree'),
    ])
    def test_up(self, url_suffix, count, expected_suffix):
        url_base = 'https://example.com'
        url = QUrl(url_base + url_suffix)
        assert url.isValid()

        new = navigate.path_up(url, count)
        assert new == QUrl(url_base + expected_suffix)

    def test_invalid_url(self):
        with pytest.raises(urlutils.InvalidUrlError):
            navigate.path_up(QUrl(), count=1)


class TestStrip:

    @pytest.mark.parametrize('url_suffix', [
        '?foo=bar',
        '#label',
        '?foo=bar#label',
    ])
    def test_strip(self, url_suffix):
        url_base = 'https://example.com/test'
        url = QUrl(url_base + url_suffix)
        assert url.isValid()

        stripped = navigate.strip(url, count=1)
        assert stripped.isValid()
        assert stripped == QUrl(url_base)

    def test_count(self):
        with pytest.raises(navigate.Error, match='Count is not supported'):
            navigate.strip(QUrl('https://example.com/'), count=2)

    def test_invalid_url(self):
        with pytest.raises(urlutils.InvalidUrlError):
            navigate.strip(QUrl(), count=1)