Completed
Pull Request — master (#617)
by
unknown
01:00
created

tests.test_echo_unknown_extension_error()   A

Complexity

Conditions 3

Size

Total Lines 15

Duplication

Lines 0
Ratio 0 %
Metric Value
cc 3
dl 0
loc 15
rs 9.4286
1
import os
2
import json
3
import pytest
4
5
from click.testing import CliRunner
6
7
from cookiecutter.cli import main
8
from cookiecutter.main import cookiecutter
9
from cookiecutter import utils, config
10
11
runner = CliRunner()
12
13
14
@pytest.fixture
15
def remove_fake_project_dir(request):
16
    """
17
    Remove the fake project directory created during the tests.
18
    """
19
    def fin_remove_fake_project_dir():
20
        if os.path.isdir('fake-project'):
21
            utils.rmtree('fake-project')
22
    request.addfinalizer(fin_remove_fake_project_dir)
23
24
25
@pytest.fixture
26
def make_fake_project_dir(request):
27
    """Create a fake project to be overwritten in the according tests."""
28
    os.makedirs('fake-project')
29
30
31
@pytest.fixture(params=['-V', '--version'])
32
def version_cli_flag(request):
33
    return request.param
34
35
36
def test_cli_version(version_cli_flag):
37
    result = runner.invoke(main, [version_cli_flag])
38
    assert result.exit_code == 0
39
    assert result.output.startswith('Cookiecutter')
40
41
42
@pytest.mark.usefixtures('make_fake_project_dir', 'remove_fake_project_dir')
43
def test_cli_error_on_existing_output_directory():
44
    result = runner.invoke(main, ['tests/fake-repo-pre/', '--no-input'])
45
    assert result.exit_code != 0
46
    expected_error_msg = 'Error: "fake-project" directory already exists\n'
47
    assert result.output == expected_error_msg
48
49
50
@pytest.mark.usefixtures('remove_fake_project_dir')
51
def test_cli():
52
    result = runner.invoke(main, ['tests/fake-repo-pre/', '--no-input'])
53
    assert result.exit_code == 0
54
    assert os.path.isdir('fake-project')
55
56
57
@pytest.mark.usefixtures('remove_fake_project_dir')
58
def test_cli_verbose():
59
    result = runner.invoke(main, ['tests/fake-repo-pre/', '--no-input', '-v'])
60
    assert result.exit_code == 0
61
    assert os.path.isdir('fake-project')
62
63
64
@pytest.mark.usefixtures('remove_fake_project_dir')
65
def test_cli_replay(mocker):
66
    mock_cookiecutter = mocker.patch(
67
        'cookiecutter.cli.cookiecutter'
68
    )
69
70
    template_path = 'tests/fake-repo-pre/'
71
    result = runner.invoke(main, [
72
        template_path,
73
        '--replay',
74
        '-v'
75
    ])
76
77
    assert result.exit_code == 0
78
    mock_cookiecutter.assert_called_once_with(
79
        template_path,
80
        None,
81
        False,
82
        replay=True,
83
        overwrite_if_exists=False,
84
        output_dir='.',
85
        config_file=config.USER_CONFIG_PATH
86
    )
87
88
89
@pytest.mark.usefixtures('remove_fake_project_dir')
90
def test_cli_exit_on_noinput_and_replay(mocker):
91
    mock_cookiecutter = mocker.patch(
92
        'cookiecutter.cli.cookiecutter',
93
        side_effect=cookiecutter
94
    )
95
96
    template_path = 'tests/fake-repo-pre/'
97
    result = runner.invoke(main, [
98
        template_path,
99
        '--no-input',
100
        '--replay',
101
        '-v'
102
    ])
103
104
    assert result.exit_code == 1
105
106
    expected_error_msg = (
107
        "You can not use both replay and no_input or extra_context "
108
        "at the same time."
109
    )
110
111
    assert expected_error_msg in result.output
112
113
    mock_cookiecutter.assert_called_once_with(
114
        template_path,
115
        None,
116
        True,
117
        replay=True,
118
        overwrite_if_exists=False,
119
        output_dir='.',
120
        config_file=config.USER_CONFIG_PATH
121
    )
122
123
124
@pytest.fixture(params=['-f', '--overwrite-if-exists'])
125
def overwrite_cli_flag(request):
126
    return request.param
127
128
129
@pytest.mark.usefixtures('remove_fake_project_dir')
130
def test_run_cookiecutter_on_overwrite_if_exists_and_replay(
131
        mocker, overwrite_cli_flag):
132
    mock_cookiecutter = mocker.patch(
133
        'cookiecutter.cli.cookiecutter',
134
        side_effect=cookiecutter
135
    )
136
137
    template_path = 'tests/fake-repo-pre/'
138
    result = runner.invoke(main, [
139
        template_path,
140
        '--replay',
141
        '-v',
142
        overwrite_cli_flag,
143
    ])
144
145
    assert result.exit_code == 0
146
147
    mock_cookiecutter.assert_called_once_with(
148
        template_path,
149
        None,
150
        False,
151
        replay=True,
152
        overwrite_if_exists=True,
153
        output_dir='.',
154
        config_file=config.USER_CONFIG_PATH
155
    )
156
157
158
@pytest.mark.usefixtures('remove_fake_project_dir')
159
def test_cli_overwrite_if_exists_when_output_dir_does_not_exist(
160
        overwrite_cli_flag):
161
    result = runner.invoke(main, [
162
        'tests/fake-repo-pre/', '--no-input', overwrite_cli_flag
163
    ])
164
165
    assert result.exit_code == 0
166
    assert os.path.isdir('fake-project')
167
168
169
@pytest.mark.usefixtures('make_fake_project_dir', 'remove_fake_project_dir')
170
def test_cli_overwrite_if_exists_when_output_dir_exists(overwrite_cli_flag):
171
    result = runner.invoke(main, [
172
        'tests/fake-repo-pre/', '--no-input', overwrite_cli_flag
173
    ])
174
175
    assert result.exit_code == 0
176
    assert os.path.isdir('fake-project')
177
178
179
@pytest.fixture(params=['-o', '--output-dir'])
180
def output_dir_flag(request):
181
    return request.param
182
183
184
@pytest.fixture
185
def output_dir(tmpdir):
186
    return str(tmpdir.mkdir('output'))
187
188
189
def test_cli_output_dir(mocker, output_dir_flag, output_dir):
190
    mock_cookiecutter = mocker.patch(
191
        'cookiecutter.cli.cookiecutter'
192
    )
193
194
    template_path = 'tests/fake-repo-pre/'
195
    result = runner.invoke(main, [
196
        template_path,
197
        output_dir_flag,
198
        output_dir
199
    ])
200
201
    assert result.exit_code == 0
202
    mock_cookiecutter.assert_called_once_with(
203
        template_path,
204
        None,
205
        False,
206
        replay=False,
207
        overwrite_if_exists=False,
208
        output_dir=output_dir,
209
        config_file=config.USER_CONFIG_PATH
210
    )
211
212
213
@pytest.fixture(params=['-h', '--help', 'help'])
214
def help_cli_flag(request):
215
    return request.param
216
217
218
def test_cli_help(help_cli_flag):
219
    result = runner.invoke(main, [help_cli_flag])
220
    assert result.exit_code == 0
221
    assert result.output.startswith('Usage')
222
223
224
@pytest.fixture
225
def user_config_path(tmpdir):
226
    return str(tmpdir.join('tests/config.yaml'))
227
228
229
def test_user_config(mocker, user_config_path):
230
    mock_cookiecutter = mocker.patch(
231
        'cookiecutter.cli.cookiecutter'
232
    )
233
234
    template_path = 'tests/fake-repo-pre/'
235
    result = runner.invoke(main, [
236
        template_path,
237
        '--config-file',
238
        user_config_path
239
    ])
240
241
    assert result.exit_code == 0
242
    mock_cookiecutter.assert_called_once_with(
243
        template_path,
244
        None,
245
        False,
246
        replay=False,
247
        overwrite_if_exists=False,
248
        output_dir='.',
249
        config_file=user_config_path
250
    )
251
252
253
def test_default_user_config_overwrite(mocker, user_config_path):
254
    mock_cookiecutter = mocker.patch(
255
        'cookiecutter.cli.cookiecutter'
256
    )
257
258
    template_path = 'tests/fake-repo-pre/'
259
    result = runner.invoke(main, [
260
        template_path,
261
        '--config-file',
262
        user_config_path,
263
        '--default-config'
264
    ])
265
266
    assert result.exit_code == 0
267
    mock_cookiecutter.assert_called_once_with(
268
        template_path,
269
        None,
270
        False,
271
        replay=False,
272
        overwrite_if_exists=False,
273
        output_dir='.',
274
        config_file=None
275
    )
276
277
278
def test_default_user_config(mocker):
279
    mock_cookiecutter = mocker.patch(
280
        'cookiecutter.cli.cookiecutter'
281
    )
282
283
    template_path = 'tests/fake-repo-pre/'
284
    result = runner.invoke(main, [
285
        template_path,
286
        '--default-config'
287
    ])
288
289
    assert result.exit_code == 0
290
    mock_cookiecutter.assert_called_once_with(
291
        template_path,
292
        None,
293
        False,
294
        replay=False,
295
        overwrite_if_exists=False,
296
        output_dir='.',
297
        config_file=None
298
    )
299
300
301
def test_echo_undefined_variable_error(tmpdir):
302
    output_dir = str(tmpdir.mkdir('output'))
303
    template_path = 'tests/undefined-variable/file-name/'
304
305
    result = runner.invoke(main, [
306
        '--no-input',
307
        '--default-config',
308
        '--output-dir',
309
        output_dir,
310
        template_path,
311
    ])
312
313
    assert result.exit_code == 1
314
315
    error = "Unable to create file '{{cookiecutter.foobar}}'"
316
    assert error in result.output
317
318
    message = "Error message: 'dict object' has no attribute 'foobar'"
319
    assert message in result.output
320
321
    context = {
322
        'cookiecutter': {
323
            'github_username': 'hackebrot',
324
            'project_slug': 'testproject'
325
        }
326
    }
327
    context_str = json.dumps(context, indent=4, sort_keys=True)
328
    assert context_str in result.output
329
330
331
def test_echo_unknown_extension_error(tmpdir):
332
    output_dir = str(tmpdir.mkdir('output'))
333
    template_path = 'tests/test-extensions/'
334
335
    result = runner.invoke(main, [
336
        '--no-input',
337
        '--default-config',
338
        '--output-dir',
339
        output_dir,
340
        template_path,
341
    ])
342
343
    assert result.exit_code == 1
344
345
    assert 'Unable to load extension: ' in result.output
346