TangibleAI/mathtext-fastapi
1
1""" Parse requirements.txt and pyproject.toml and move versions to pyproject.toml """2from pathlib import Path3import re4import sys5import toml6 7def get_requirement_versions(path='requirements.txt'):8 """ Read requirements.txt file and return dict of package versions """9 path = Path(path or '')10 if path.is_dir():11 path = next(iter(path.glob('**/requirements.txt')))12 reqdict = {}13 text = Path(path).open().read()14 for line in text.splitlines():15 if line.strip():16 match = re.match(r'([-_a-zA-Z0-9]+)\s*([ >=<~^,.rabc0-9]+)\s*', line)17 if match:18 name, ver = match.groups()19 reqdict[name] = ver20 return reqdict 21 22 23def normalize_name(name):24 return str(name).strip().replace('_', '-').replace(' ', '-').lower()25 26 27def pin_versions(pyproject='pyproject.toml', reqdict=None, overwrite=False):28 if not reqdict or isinstance(reqdict, (str, Path)):29 reqdict = get_requirement_versions(path=reqdict)30 reqdict = {31 normalize_name(k): v for (k, v) in 32 reqdict.items()33 }34 35 pyproj = toml.load(pyproject)36 depdict = pyproj.get('tool', {}).get('poetry', {}).get('dependencies', {})37 depdict = {38 normalize_name(k): v for (k, v) in 39 depdict.items()40 }41 42 for name, spec in reqdict.items():43 if name in depdict:44 ver = depdict[name]45 if isinstance(ver, str) and (overwrite or ver == '*'):46 depdict[name] = spec47 48 pyproj['tool']['poetry']['dependencies'] = depdict49 overwrite = overwrite or (input(f'Overwrite {pyproject}?')[0].lower() == 'y')50 if overwrite:51 with open(pyproject, 'w') as stream:52 toml.dump(pyproj, stream)53 return pyproj54 55 56if __name__ == '__main__':57 path = 'requirements.txt'58 if sys.argv[1:]:59 path = sys.argv[1]60 pyproj = pin_versions(reqdict=path)61 print(toml.dumps(pyproj))62 63 