Coverage for src/software_citation_sync/sync.py: 92%

25 statements  

« prev     ^ index     » next       coverage.py v7.14.3, created at 2026-06-27 17:58 +0000

1# SPDX-FileCopyrightText: 2026 Arcangelo Massari <github@a.arcangelomassari.com> 

2# 

3# SPDX-License-Identifier: ISC 

4 

5from __future__ import annotations 

6 

7from software_citation_sync.cff import ( 

8 apply_citation_metadata, 

9 create_citation, 

10 load_citation, 

11 render_citation_bibtex, 

12 validate_with_cffconvert, 

13 write_citation, 

14) 

15from software_citation_sync.config import CheckResult, CitationConfig, ProjectMetadata 

16from software_citation_sync.readme import bibtex_reference, readme_block_matches, write_readme_block 

17 

18 

19def check(config: CitationConfig) -> CheckResult: 

20 errors = [*validate_with_cffconvert(config.citation_path)] 

21 bibtex = render_readme_bibtex(config) 

22 if not readme_block_matches(config.readme_path, config.version, bibtex): 

23 errors.append(f"{config.readme_path} citation block is out of date") 

24 return CheckResult(tuple(errors)) 

25 

26 

27def write_citation_metadata(config: CitationConfig, project_metadata: ProjectMetadata | None = None) -> bool: 

28 if config.citation_path.exists(): 

29 data = load_citation(config.citation_path) 

30 else: 

31 if project_metadata is None: 

32 msg = f"{config.citation_path} does not exist and project metadata was not provided" 

33 raise FileNotFoundError(msg) 

34 data = create_citation(project_metadata) 

35 apply_citation_metadata(data, config) 

36 return write_citation(config.citation_path, data) 

37 

38 

39def render_readme_bibtex(config: CitationConfig) -> str: 

40 data = load_citation(config.citation_path) 

41 return render_citation_bibtex( 

42 data, 

43 bibtex_reference(str(data["title"]), config.version), 

44 ) 

45 

46 

47def write_readme(config: CitationConfig) -> bool: 

48 bibtex = render_readme_bibtex(config) 

49 return write_readme_block(config.readme_path, config.version, bibtex)