Passed
Push — develop ( 4d6495...2dddb7 )
by Jace
03:19
created

tests.test_api.describe_list()   A

Complexity

Conditions 2

Size

Total Lines 19
Code Lines 9

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 2
eloc 9
nop 0
dl 0
loc 19
rs 9.95
c 0
b 0
f 0
1
# pylint: disable=redefined-outer-name,unused-argument,unused-variable,singleton-comparison,expression-not-assigned,no-member
2
3
import logging
4
import os
5
import shutil
6
from contextlib import suppress
7
8
import pytest
0 ignored issues
show
introduced by
Unable to import 'pytest'
Loading history...
9
from expecter import expect
0 ignored issues
show
introduced by
Unable to import 'expecter'
Loading history...
10
from freezegun import freeze_time
0 ignored issues
show
introduced by
Unable to import 'freezegun'
Loading history...
11
12
import gitman
13
from gitman import shell
14
from gitman.exceptions import InvalidRepository, UncommittedChanges
15
from gitman.models import Config
16
17
from .utilities import strip
18
19
20
ROOT = os.path.join(os.path.dirname(os.path.dirname(__file__)))
21
TMP = os.path.join(ROOT, 'tmp')
22
23
CONFIG = """
24
location: deps
25
sources:
26
- name: gitman_1
27
  repo: https://github.com/jacebrowning/gitman-demo
28
  sparse_paths:
29
  -
30
  rev: example-branch
31
  link:
32
  scripts:
33
  -
34
- name: gitman_2
35
  repo: https://github.com/jacebrowning/gitman-demo
36
  sparse_paths:
37
  -
38
  rev: example-tag
39
  link:
40
  scripts:
41
  -
42
- name: gitman_3
43
  repo: https://github.com/jacebrowning/gitman-demo
44
  sparse_paths:
45
  -
46
  rev: 9bf18e16b956041f0267c21baad555a23237b52e
47
  link:
48
  scripts:
49
  -
50
""".lstrip()
51
52
log = logging.getLogger(__name__)
53
54
55
@pytest.yield_fixture
56
def config():
57
    log.info("Temporary directory: %s", TMP)
58
59
    with suppress(FileNotFoundError, PermissionError):
60
        shutil.rmtree(TMP)
61
    with suppress(FileExistsError):
62
        os.makedirs(TMP)
63
    os.chdir(TMP)
64
65
    os.system("touch .git")
66
    config = Config(root=TMP)
67
    config.__mapper__.text = CONFIG
68
69
    log.debug("File listing: %s", os.listdir(TMP))
70
71
    yield config
72
73
    os.chdir(ROOT)
74
75
76
def describe_init():
77
78
    def it_creates_a_new_config_file(tmpdir):
79
        tmpdir.chdir()
80
81
        expect(gitman.init()) == True
82
83
        expect(Config().__mapper__.text) == strip("""
84
        location: gitman_sources
85
        sources:
86
        - name: sample_dependency
87
          repo: https://github.com/githubtraining/hellogitworld
88
          sparse_paths:
89
          -
90
          rev: master
91
          link:
92
          scripts:
93
          -
94
        sources_locked:
95
        - name: sample_dependency
96
          repo: https://github.com/githubtraining/hellogitworld
97
          sparse_paths:
98
          -
99
          rev: ebbbf773431ba07510251bb03f9525c7bab2b13a
100
          link:
101
          scripts:
102
          -
103
        """)
104
105
    def it_does_not_modify_existing_config_file(config):
106
        expect(gitman.init()) == False
107
108
        expect(config.__mapper__.text) == CONFIG
109
110
111
def describe_install():
112
113
    def it_creates_missing_directories(config):
114
        shell.rm(config.location)
115
116
        expect(gitman.install('gitman_1', depth=1)) == True
117
118
        expect(os.listdir(config.location)) == ['gitman_1']
119
120
    def it_should_not_modify_config(config):
121
        expect(gitman.install('gitman_1', depth=1)) == True
122
123
        expect(config.__mapper__.text) == CONFIG
124
125
    def it_merges_sources(config):
126
        config.__mapper__.text = strip("""
127
        location: deps
128
        sources:
129
        - name: gitman_1
130
          repo: https://github.com/jacebrowning/gitman-demo
131
          rev: example-branch
132
          link:
133
          scripts:
134
          -
135
        sources_locked:
136
        - name: gitman_2
137
          repo: https://github.com/jacebrowning/gitman-demo
138
          rev: example-branch
139
          link:
140
          scripts:
141
          -
142
        - name: gitman_3
143
          repo: https://github.com/jacebrowning/gitman-demo
144
          rev: 7bd138fe7359561a8c2ff9d195dff238794ccc04
145
          link:
146
          scripts:
147
          -
148
        """)
149
150
        expect(gitman.install(depth=1)) == True
151
152
        expect(len(os.listdir(config.location))) == 3
153
154
    def it_can_handle_missing_locked_sources(config):
155
        config.__mapper__.text = strip("""
156
        location: deps
157
        sources:
158
        - name: gitman_1
159
          repo: https://github.com/jacebrowning/gitman-demo
160
          rev: example-branch
161
          link:
162
          scripts:
163
          -
164
        sources_locked:
165
        - name: gitman_2
166
          repo: https://github.com/jacebrowning/gitman-demo
167
          rev: 7bd138fe7359561a8c2ff9d195dff238794ccc04
168
          link:
169
          scripts:
170
          -
171
        """)
172
173
        expect(gitman.install('gitman_1', depth=1)) == True
174
175
        expect(os.listdir(config.location)) == ['gitman_1']
176
177
    def it_detects_invalid_repositories(config):
178
        shell.rm(os.path.join("deps", "gitman_1", ".git"))
179
        shell.mkdir(os.path.join("deps", "gitman_1", ".git"))
180
181
        try:
182
            with pytest.raises(InvalidRepository):
183
                expect(gitman.install('gitman_1', depth=1)) == False
184
185
        finally:
186
            shell.rm(os.path.join("deps", "gitman_1"))
187
188
    def describe_links():
189
190
        @pytest.fixture
191
        def config_with_link(config):
192
            config.__mapper__.text = strip("""
193
            location: deps
194
            sources:
195
            - name: gitman_1
196
              repo: https://github.com/jacebrowning/gitman-demo
197
              rev: 7bd138fe7359561a8c2ff9d195dff238794ccc04
198
              link: my_link
199
              scripts:
200
              -
201
            """)
202
203
            return config
204
205
        @pytest.mark.xfail(os.name == 'nt', reason="No symlinks on Windows")
206
        def it_should_create_links(config_with_link):
207
            expect(gitman.install(depth=1)) == True
208
209
            expect(os.listdir()).contains('my_link')
210
211
        @pytest.mark.xfail(os.name == 'nt', reason="No symlinks on Windows")
212
        def it_should_not_overwrite_files(config_with_link):
213
            os.system("touch my_link")
214
215
            with pytest.raises(RuntimeError):
216
                gitman.install(depth=1)
217
218
        @pytest.mark.xfail(os.name == 'nt', reason="No symlinks on Windows")
219
        def it_overwrites_files_with_force(config_with_link):
220
            os.system("touch my_link")
221
222
            expect(gitman.install(depth=1, force=True)) == True
223
224
    def describe_scripts():
225
226
        @pytest.fixture
227
        def config_with_scripts(config):
228
            config.__mapper__.text = strip("""
229
            location: deps
230
            sources:
231
            - name: gitman_1
232
              repo: https://github.com/jacebrowning/gitman-demo
233
              rev: 7bd138fe7359561a8c2ff9d195dff238794ccc04
234
              link:
235
              scripts:
236
              - make foobar
237
            """)
238
239
            return config
240
241
        def it_detects_failures_in_scripts(config_with_scripts):
242
            with pytest.raises(RuntimeError):
243
                expect(gitman.install())
244
245
        def script_failures_can_be_ignored(config_with_scripts):
246
            expect(gitman.install(force=True)) == True
247
248
    def describe_sparse_paths():
249
        @pytest.fixture
250
        def config_with_scripts(config):
251
            config.__mapper__.text = strip("""
252
                    location: deps
253
                    sources:
254
                    - name: gitman_1
255
                      repo: https://github.com/jacebrowning/gitman-demo
256
                      sparse_paths:
257
                      - src/*
258
                      rev: ddbe17ef173538d1fda29bd99a14bab3c5d86e78
259
                      link:
260
                      scripts:
261
                      -
262
                    """)
263
264
            return config
265
266
        def it_successfully_materializes_the_repo(config):
267
            expect(gitman.install(depth=1, force=True)) == True
268
            dir_listing = os.listdir(os.path.join(config.location, "gitman_1"))
269
            expect(dir_listing).contains('src')
270
271
        def it_contains_only_the_sparse_paths(config):
272
            expect(gitman.install(depth=1, force=True)) == True
273
            dir_listing = os.listdir(os.path.join(config.location, "gitman_1"))
274
            expect(dir_listing).contains('src')
275
            expect(len(dir_listing) == 1)
276
277
278
def describe_uninstall():
279
280
    def it_deletes_dependencies_when_they_exist(config):
281
        gitman.install('gitman_1', depth=1)
282
        expect(os.path.isdir(config.location)) == True
283
284
        expect(gitman.uninstall()) == True
285
286
        expect(os.path.exists(config.location)) == False
287
288
    def it_should_not_fail_when_no_dependnecies_exist(config):
289
        expect(os.path.isdir(config.location)) == False
290
291
        expect(gitman.uninstall()) == True
292
293
    def it_deletes_the_log_file(config):
294
        gitman.install('gitman_1', depth=1)
295
        gitman.list()
296
        expect(os.path.exists(config.log_path)) == True
297
298
        gitman.uninstall()
299
        expect(os.path.exists(config.log_path)) == False
300
301
302
def describe_keep_location():
303
304
    def it_deletes_dependencies_when_they_exist(config):
305
        gitman.install('gitman_1', depth=1)
306
        expect(os.path.isdir(config.location)) == True
307
308
        expect(gitman.uninstall(keep_location=True)) == True
309
310
        path = os.path.join(config.location, 'gitman_1')
311
        expect(os.path.exists(path)) == False
312
313
        expect(os.path.exists(config.location)) == True
314
315
        gitman.uninstall()
316
317
    def it_should_not_fail_when_no_dependencies_exist(config):
318
        expect(os.path.isdir(config.location)) == False
319
320
        expect(gitman.uninstall(keep_location=True)) == True
321
322
        gitman.uninstall()
323
324
    def it_deletes_the_log_file(config):
325
        gitman.install('gitman_1', depth=1)
326
        gitman.list()
327
        expect(os.path.exists(config.log_path)) == True
328
329
        gitman.uninstall(keep_location=True)
330
        expect(os.path.exists(config.log_path)) == False
331
332
        gitman.uninstall()
333
334
335
def describe_update():
336
337
    def it_should_not_modify_config(config):
338
        gitman.update('gitman_1', depth=1)
339
340
        expect(config.__mapper__.text) == CONFIG
341
342
    def it_locks_previously_locked_dependnecies(config):
343
        config.__mapper__.text = strip("""
344
        location: deps
345
        sources:
346
        - name: gitman_1
347
          repo: https://github.com/jacebrowning/gitman-demo
348
          sparse_paths:
349
          -
350
          rev: example-branch
351
          link:
352
          scripts:
353
          -
354
        - name: gitman_2
355
          repo: https://github.com/jacebrowning/gitman-demo
356
          sparse_paths:
357
          -
358
          rev: example-tag
359
          link:
360
          scripts:
361
          -
362
        sources_locked:
363
        - name: gitman_2
364
          repo: https://github.com/jacebrowning/gitman-demo
365
          sparse_paths:
366
          -
367
          rev: (old revision)
368
          link:
369
          scripts:
370
          -
371
        """)
372
373
        gitman.update(depth=1)
374
375
        expect(config.__mapper__.text) == strip("""
376
        location: deps
377
        sources:
378
        - name: gitman_1
379
          repo: https://github.com/jacebrowning/gitman-demo
380
          sparse_paths:
381
          -
382
          rev: example-branch
383
          link:
384
          scripts:
385
          -
386
        - name: gitman_2
387
          repo: https://github.com/jacebrowning/gitman-demo
388
          sparse_paths:
389
          -
390
          rev: example-tag
391
          link:
392
          scripts:
393
          -
394
        sources_locked:
395
        - name: gitman_2
396
          repo: https://github.com/jacebrowning/gitman-demo
397
          sparse_paths:
398
          -
399
          rev: 7bd138fe7359561a8c2ff9d195dff238794ccc04
400
          link:
401
          scripts:
402
          -
403
        """)
404
405
    def it_should_not_lock_dependnecies_when_disabled(config):
406
        config.__mapper__.text = strip("""
407
        location: deps
408
        sources:
409
        - name: gitman_1
410
          repo: https://github.com/jacebrowning/gitman-demo
411
          sparse_paths:
412
          -
413
          rev: example-branch
414
          link:
415
          scripts:
416
          -
417
        - name: gitman_2
418
          repo: https://github.com/jacebrowning/gitman-demo
419
          sparse_paths:
420
          -
421
          rev: example-tag
422
          link:
423
          scripts:
424
          -
425
        sources_locked:
426
        - name: gitman_2
427
          repo: https://github.com/jacebrowning/gitman-demo
428
          sparse_paths:
429
          -
430
          rev: (old revision)
431
          link:
432
          scripts:
433
          -
434
        """)
435
436
        gitman.update(depth=1, lock=False)
437
438
        expect(config.__mapper__.text) == strip("""
439
        location: deps
440
        sources:
441
        - name: gitman_1
442
          repo: https://github.com/jacebrowning/gitman-demo
443
          sparse_paths:
444
          -
445
          rev: example-branch
446
          link:
447
          scripts:
448
          -
449
        - name: gitman_2
450
          repo: https://github.com/jacebrowning/gitman-demo
451
          sparse_paths:
452
          -
453
          rev: example-tag
454
          link:
455
          scripts:
456
          -
457
        sources_locked:
458
        - name: gitman_2
459
          repo: https://github.com/jacebrowning/gitman-demo
460
          sparse_paths:
461
          -
462
          rev: (old revision)
463
          link:
464
          scripts:
465
          -
466
        """)
467
468
    def it_should_lock_all_dependencies_when_enabled(config):
469
        gitman.update(depth=1, lock=True)
470
471
        expect(config.__mapper__.text) == CONFIG + strip("""
472
        sources_locked:
473
        - name: gitman_1
474
          repo: https://github.com/jacebrowning/gitman-demo
475
          sparse_paths:
476
          -
477
          rev: 1de84ca1d315f81b035cd7b0ecf87ca2025cdacd
478
          link:
479
          scripts:
480
          -
481
        - name: gitman_2
482
          repo: https://github.com/jacebrowning/gitman-demo
483
          sparse_paths:
484
          -
485
          rev: 7bd138fe7359561a8c2ff9d195dff238794ccc04
486
          link:
487
          scripts:
488
          -
489
        - name: gitman_3
490
          repo: https://github.com/jacebrowning/gitman-demo
491
          sparse_paths:
492
          -
493
          rev: 9bf18e16b956041f0267c21baad555a23237b52e
494
          link:
495
          scripts:
496
          -
497
        """)
498
499
500
def describe_list():
501
502
    @freeze_time("2012-01-14 12:00:01")
503
    def it_updates_the_log(config):
504
        gitman.install()
505
        gitman.list()
506
507
        with open(config.log_path) as stream:
508
            contents = stream.read().replace(TMP, "tmp").replace('\\', '/')
509
        expect(contents) == strip("""
510
        2012-01-14 12:00:01
511
        tmp/deps/gitman_1: https://github.com/jacebrowning/gitman-demo @ 1de84ca1d315f81b035cd7b0ecf87ca2025cdacd
512
        tmp/deps/gitman_1/gitman_sources/gdm_3: https://github.com/jacebrowning/gdm-demo @ 050290bca3f14e13fd616604202b579853e7bfb0
513
        tmp/deps/gitman_1/gitman_sources/gdm_3/gitman_sources/gdm_3: https://github.com/jacebrowning/gdm-demo @ fb693447579235391a45ca170959b5583c5042d8
514
        tmp/deps/gitman_1/gitman_sources/gdm_3/gitman_sources/gdm_4: https://github.com/jacebrowning/gdm-demo @ 63ddfd82d308ddae72d31b61cb8942c898fa05b5
515
        tmp/deps/gitman_1/gitman_sources/gdm_4: https://github.com/jacebrowning/gdm-demo @ 63ddfd82d308ddae72d31b61cb8942c898fa05b5
516
        tmp/deps/gitman_2: https://github.com/jacebrowning/gitman-demo @ 7bd138fe7359561a8c2ff9d195dff238794ccc04
517
        tmp/deps/gitman_3: https://github.com/jacebrowning/gitman-demo @ 9bf18e16b956041f0267c21baad555a23237b52e
518
        """, end='\n\n')
519
520
521
def describe_lock():
522
523
    def it_records_all_versions_when_no_arguments(config):
524
        expect(gitman.update(depth=1, lock=False)) == True
525
        expect(gitman.lock()) == True
526
527
        expect(config.__mapper__.text) == CONFIG + strip("""
528
        sources_locked:
529
        - name: gitman_1
530
          repo: https://github.com/jacebrowning/gitman-demo
531
          sparse_paths:
532
          -
533
          rev: 1de84ca1d315f81b035cd7b0ecf87ca2025cdacd
534
          link:
535
          scripts:
536
          -
537
        - name: gitman_2
538
          repo: https://github.com/jacebrowning/gitman-demo
539
          sparse_paths:
540
          -
541
          rev: 7bd138fe7359561a8c2ff9d195dff238794ccc04
542
          link:
543
          scripts:
544
          -
545
        - name: gitman_3
546
          repo: https://github.com/jacebrowning/gitman-demo
547
          sparse_paths:
548
          -
549
          rev: 9bf18e16b956041f0267c21baad555a23237b52e
550
          link:
551
          scripts:
552
          -
553
        """) == config.__mapper__.text
554
555
    def it_records_specified_dependencies(config):
556
        expect(gitman.update(depth=1, lock=False)) == True
557
        expect(gitman.lock('gitman_1', 'gitman_3')) == True
558
559
        expect(config.__mapper__.text) == CONFIG + strip("""
560
        sources_locked:
561
        - name: gitman_1
562
          repo: https://github.com/jacebrowning/gitman-demo
563
          sparse_paths:
564
          -
565
          rev: 1de84ca1d315f81b035cd7b0ecf87ca2025cdacd
566
          link:
567
          scripts:
568
          -
569
        - name: gitman_3
570
          repo: https://github.com/jacebrowning/gitman-demo
571
          sparse_paths:
572
          -
573
          rev: 9bf18e16b956041f0267c21baad555a23237b52e
574
          link:
575
          scripts:
576
          -
577
        """) == config.__mapper__.text
578
579
    def it_should_fail_on_dirty_repositories(config):
580
        expect(gitman.update(depth=1, lock=False)) == True
581
        shell.rm(os.path.join("deps", "gitman_1", ".project"))
582
583
        try:
584
            with pytest.raises(UncommittedChanges):
585
                gitman.lock()
586
587
            expect(config.__mapper__.text).does_not_contain("<dirty>")
588
589
        finally:
590
            shell.rm(os.path.join("deps", "gitman_1"))
591
592
    def it_should_fail_on_missing_repositories(config):
593
        shell.mkdir("deps")
594
        shell.rm(os.path.join("deps", "gitman_1"))
595
596
        with pytest.raises(InvalidRepository):
597
            gitman.lock()
598
599
        expect(config.__mapper__.text).does_not_contain("<unknown>")
600
601
    def it_should_fail_on_invalid_repositories(config):
602
        shell.mkdir("deps")
603
        shell.rm(os.path.join("deps", "gitman_1", ".git"))
604
        shell.mkdir(os.path.join("deps", "gitman_1", ".git"))
605
606
        try:
607
            with pytest.raises(InvalidRepository):
608
                gitman.lock()
609
610
            expect(config.__mapper__.text).does_not_contain("<unknown>")
611
612
        finally:
613
            shell.rm(os.path.join("deps", "gitman_1"))
614